Subversion Repositories lagranto.arpege

Rev

Details | Last modification | View Log | RSS feed

Rev Author Line No. Line
3 michaesp 1
      PROGRAM reformat
2
 
3
c     ***********************************************************************
4
c     * Change format of a trajectory file                                  *
5
c     * Michael Sprenger / Spring, summer 2010                              *
6
c     ***********************************************************************
7
 
8
      implicit none
9
 
10
c     ----------------------------------------------------------------------
11
c     Declaration of variables
12
c     ----------------------------------------------------------------------
13
 
14
c     Mode & Special parameters depending on mode
15
      character*80                           mode
16
      real                                   clon,clat,radius
17
 
18
c     Input and output files
19
      character*80                           inpfile     ! Input filename
20
      character*80                           outfile     ! Output filename
21
 
22
c     Trajectories
23
      integer                                ntra        ! Number of trajectories
24
      integer                                ntim        ! Number of times
25
      integer                                ncol        ! Number of columns
26
      real,allocatable, dimension (:,:,:) :: tra         ! Trajectories (ntra,ntim,ncol)
27
      real,allocatable, dimension (:,:)   :: proxy       ! Footprint
28
      character*80                           vars(100)   ! Variable names
29
      integer                                refdate(6)  ! Reference date
30
      real,allocatable, dimension (:)     :: num         ! Output number
31
 
32
c     Auxiliary variables
33
      integer                                inpmode
34
      integer                                stat
35
      integer                                fid
36
      integer                                i,j,k
37
      real                                   dist
38
      real                                   lon0,lat0,lon1,lat1
39
 
40
c     Externals
41
      real                                   sdis
42
      external                               sdis
43
 
44
c     ----------------------------------------------------------------------
45
c     Preparations
46
c     ----------------------------------------------------------------------
47
 
48
c     Read parameters
49
      open(10,file='traj2num.param')
50
       read(10,*) inpfile
51
       read(10,*) outfile
52
       read(10,*) ntra,ntim,ncol
53
       read(10,*) mode
54
       if ( mode.eq.'proxy' ) then
55
          read(10,*) clon
56
          read(10,*) clat
57
          read(10,*) radius
58
       endif
59
      close(10)
60
 
61
c     Check that a valid mode is selected
62
      if ( mode.eq.'boost' ) goto 10
63
      if ( mode.eq.'proxy' ) goto 10
64
      print*,' Unknown mode ',trim(mode)
65
      stop
66
 10   continue
67
 
68
c     Determine the formats
69
      call mode_tra(inpmode,inpfile)
70
      if (inpmode.eq.-1) inpmode=1
71
 
72
c     Allocate memory
73
      allocate(tra(ntra,ntim,ncol),stat=stat)
74
      if (stat.ne.0) print*,'*** error allocating array tra      ***' 
75
      allocate(num(ntra),stat=stat)
76
      if (stat.ne.0) print*,'*** error allocating array num      ***'
77
      if ( mode.eq. 'proxy' ) then
78
           allocate(proxy(ntra,ncol+1),stat=stat)
79
           if (stat.ne.0) print*,'*** error allocating array proxy  ***'  
80
      endif
81
 
82
c     Read inpufile
83
      call ropen_tra(fid,inpfile,ntra,ntim,ncol,refdate,vars,inpmode)
84
      call read_tra (fid,tra,ntra,ntim,ncol,inpmode)
85
      call close_tra(fid,inpmode)
86
 
87
c     ----------------------------------------------------------------------
88
c     Mode = 'boost': get the maximum distance traveled in one time step
89
c     ----------------------------------------------------------------------
90
 
91
      if ( mode.ne.'boost') goto 100
92
 
93
      do i=1,ntra
94
 
95
        num(i) = 0.
96
 
97
        do j=2,ntim
98
 
99
c          Get spherical distance between data points
100
           lon0 = tra(i,j-1,2)
101
           lat0 = tra(i,j-1,3)
102
           lon1 = tra(i,j  ,2)
103
           lat1 = tra(i,j  ,3)
104
           dist = sdis( lon1,lat1,lon0,lat0 )
105
 
106
           if ( dist.gt.num(i) ) num(i) = dist
107
 
108
        enddo
109
 
110
      enddo
111
 
112
 100  continue
113
 
114
c     ----------------------------------------------------------------------
115
c     Mode = 'proxy': get nearest distance to a lat/lon point
116
c     ----------------------------------------------------------------------
117
 
118
      if ( mode.ne.'proxy') goto 200
119
 
120
          call get_proxy (proxy,clon,clat,tra,ntra,ntim,ncol,radius)
121
          do i=1,ntra
122
            num(i) = proxy(i,ncol+1)
123
          enddo
124
 
125
 200  continue
126
 
127
c     ----------------------------------------------------------------------
128
c     Write output file
129
c     ----------------------------------------------------------------------
130
 
131
      open(10,file=outfile)
132
        do i=1,ntra
133
            write(10,*) num(i)
134
        enddo
135
      close(10)
136
 
137
      end
138
 
139
c     ***********************************************************************
140
c     * SUBROUTINES                                                         *
141
c     ***********************************************************************
142
 
143
c     -----------------------------------------------------------------------
144
c     Spherical distance between lat/lon points
145
c     -----------------------------------------------------------------------
146
 
147
      real function sdis(xp,yp,xq,yq)
148
c
149
c     calculates spherical distance (in km) between two points given
150
c     by their spherical coordinates (xp,yp) and (xq,yq), respectively.
151
c
152
      real      re
153
      parameter (re=6370.)
154
      real      pi180
155
      parameter (pi180=3.14159/180.)
156
      real      xp,yp,xq,yq,arg
157
 
158
      arg=sin(pi180*yp)*sin(pi180*yq)+
159
     >    cos(pi180*yp)*cos(pi180*yq)*cos(pi180*(xp-xq))
160
      if (arg.lt.-1.) arg=-1.
161
      if (arg.gt.1.) arg=1.
162
 
163
      sdis=re*acos(arg)
164
 
165
      end
166
 
167
c     -----------------------------------------------------------------------
168
c     Nearest distance to a lat/lon point
169
c     -----------------------------------------------------------------------
170
 
171
      subroutine get_proxy (proxy,clon,clat,tra,ntra,ntim,ncol,radius)
172
 
173
c     Given a set of trajectories tra(ntra,ntim,ncol), find the closest point
174
c     to clon/clat and return the footprint of this trajectory at this
175
c     point: proxy(ntra,ncol+1); the parameter <ncol+1> of the trajectory will
176
c     become the minimum distance.
177
 
178
      implicit none
179
 
180
c     Declaration of parameters
181
      integer    ntra,ntim,ncol
182
      real       tra(ntra,ntim,ncol)
183
      real       proxy(ntra,ncol+1)
184
      real       radius
185
      real       clon,clat
186
 
187
c     Flag for tests
188
      integer      test
189
      parameter    (test=0)
190
      character*80 testfile
191
      parameter    (testfile='TEST.nc')
192
 
193
c     Number of grid points for the radius mask
194
      integer      nmax 
195
      parameter    (nmax = 400)     
196
      real         degkm
197
      parameter    (degkm = 111.)
198
 
199
c     Number of binary search steps
200
      integer      nbin
201
      parameter    (nbin=10)
202
 
203
c     Auxiliry variables
204
      integer      i,j,k
205
      real         lon,lat,rlon,rlat
206
      real         dist
207
      character*80 varname
208
      integer      rnx,rny
209
      real         rmask (nmax,nmax)
210
      real         rcount(nmax,nmax)
211
      real         rxmin,rymin,rdx,rdy
212
      integer      indx,indy
213
      integer      isnear
214
      real         near,near0,near1,nearm
215
      integer      j0,j1
216
      real         r0,r1,rm,frac
217
      real         rlon0,rlon1,rlonm,rlat0,rlat1,rlatm
218
 
219
c     Externals
220
      real       sdis
221
      external   sdis
222
 
223
c     Transform into clon/clat centered system
224
      do i=1,ntra
225
        do j=1,ntim
226
            lon = tra(i,j,2)
227
            lat = tra(i,j,3)
228
            call getenvir_f (clon,clat,0.,rlon,rlat,lon,lat,1)
229
            tra(i,j,2) = rlon
230
            tra(i,j,3) = rlat
231
        enddo
232
      enddo
233
 
234
c     Init the radius mask - define the grid resolution
235
      rdx   = 2.5 * radius / degkm / real(nmax)
236
      rdy   = 2.5 * radius / degkm / real(nmax)
237
      rnx   = nmax
238
      rny   = nmax
239
      rxmin = -real(rnx/2)*rdx
240
      rymin = -real(rny/2)*rdy
241
      do i=1,rnx
242
         do j=1,rny
243
              rlon = rxmin + real(i-1) * rdx
244
              rlat = rymin + real(j-1) * rdy
245
              dist = sdis(rlon,rlat,0.,0.)
246
              if ( dist.lt.radius ) then
247
                 rmask(i,j) = dist
248
              else
249
                rmask(i,j) = radius
250
              endif
251
         enddo
252
      enddo
253
 
254
c     Init counter for test
255
      if ( test.eq.1 ) then
256
        do i=1,rnx
257
          do j=1,rny
258
            rcount(i,j) = 0.
259
          enddo
260
        enddo
261
      endif
262
 
263
 
264
c     Loop over all trajectories
265
      do i=1,ntra
266
 
267
c        Decide whether trajectory comes close to point   
268
         isnear = 0
269
         near   = radius
270
         do j=1,ntim
271
            indx = nint( ( tra(i,j,2) - rxmin ) / rdx + 1. )
272
            indy = nint( ( tra(i,j,3) - rymin ) / rdy + 1. )
273
            if ( (indx.ge.1).and.(indx.le.rnx).and.
274
     >           (indy.ge.1).and.(indy.le.rny) )
275
     >      then
276
               if (rmask(indx,indy).lt.near) then
277
                   near   = rmask(indx,indy)
278
                   isnear = j
279
               endif
280
            endif
281
         enddo
282
 
283
c        No close point was found - go to next trajectory
284
         do k=1,ncol
285
            proxy(i,k) = tra(i,1,k)
286
         enddo
287
         proxy(i,ncol+1) = radius
288
         if ( isnear.eq.0 ) goto 310
289
 
290
c        Get the exact position and time with binary search
291
         j0 = isnear - 1
292
         if ( j0.eq.0 ) j0 = 1
293
         rlon0 = tra(i,j0,2)
294
         rlat0 = tra(i,j0,3)
295
         near0 = sdis(rlon0,rlat0,0.,0.)
296
         r0    = real(j0)
297
 
298
         j1 = isnear + 1
299
         if ( j1.gt.ntim ) j1 = ntim
300
         rlon1 = tra(i,j1,2)
301
         rlat1 = tra(i,j1,3)
302
         near1 = sdis(tra(i,j1,2),tra(i,j1,3),0.,0.)
303
         r1    = real(j1)
304
 
305
         do k=1,nbin
306
            rm    = 0.5 * ( r0 + r1 )
307
            rlatm = 0.5 * ( rlat0 + rlat1 )
308
            rlonm = 0.5 * ( rlon0 + rlon1 )
309
            nearm = sdis(rlonm,rlatm,0.,0.)
310
            if ( near0.lt.near1 ) then
311
               r1    = rm
312
               rlon1 = rlonm
313
               rlat1 = rlatm
314
               near1 = nearm
315
            else
316
               r0    = rm
317
               rlon0 = rlonm
318
               rlat0 = rlatm
319
               near0 = nearm
320
            endif
321
         enddo
322
 
323
c        Now get the final distance and position
324
         proxy(i,ncol+1) = nearm
325
         if ( test.eq.1 ) then
326
            indx = nint( ( rlonm - rxmin ) / rdx + 1. )
327
            indy = nint( ( rlatm - rymin ) / rdy + 1. )
328
            if ( (indx.ge.1).and.(indx.le.rnx).and.
329
     >           (indy.ge.1).and.(indy.le.rny) )
330
     >      then
331
               rcount(indx,indy) = rcount(indx,indy) + 1.
332
            endif
333
         endif
334
 
335
c        Get all values at exactly this position
336
         j0   = int(rm)
337
         frac = rm - real(j0)
338
         j1 = j0 + 1
339
         if (j1.gt.ntim ) j1 = ntim
340
         do k=1,ncol
341
            proxy(i,k) = (1.-frac)*tra(i,j0,k)+frac*tra(i,j1,k)
342
         enddo
343
 
344
c        Next trajectory
345
310      continue
346
 
347
      enddo
348
 
349
c     Write radius mask to netCDF file for tests
350
      if ( test.eq.1 ) then
351
        varname = 'MASK'
352
        call writecdf2D(testfile,varname,rmask,0.,
353
     >                    rdx,rdy,rxmin,rymin,rnx,rny,1,1)
354
        varname = 'COUNT'
355
        call writecdf2D(testfile,varname,rcount,0.,
356
     >                    rdx,rdy,rxmin,rymin,rnx,rny,0,1)
357
      endif
358
 
359
      end
360
 
361
 
362
 
363
c     --------------------------------------------------------------------------------
364
c     Forward coordinate transformation (True lon/lat -> Rotated lon/lat)
365
c     --------------------------------------------------------------------------------
366
 
367
      SUBROUTINE getenvir_f (clon,clat,rotation,
368
     >                       rlon,rlat,lon,lat,n)
369
 
370
      implicit none
371
 
372
c     Declaration of input and output parameters
373
      integer     n
374
      real        clon,clat,rotation
375
      real        lon(n), lat(n)
376
      real        rlon(n),rlat(n)
377
 
378
c     Auxiliary variables 
379
      real         pollon,pollat
380
      integer      i
381
      real         rlon1(n),rlat1(n)
382
 
383
c     Externals
384
      real     lmtolms,phtophs
385
      external lmtolms,phtophs
386
 
387
c     First rotation
388
      pollon=clon-180.
389
      if (pollon.lt.-180.) pollon=pollon+360.
390
      pollat=90.-clat
391
      do i=1,n
392
 
393
c        First rotation
394
         pollon=clon-180.
395
         if (pollon.lt.-180.) pollon=pollon+360.
396
         pollat=90.-clat
397
         rlon1(i)=lmtolms(lat(i),lon(i),pollat,pollon)
398
         rlat1(i)=phtophs(lat(i),lon(i),pollat,pollon)            
399
 
400
c        Second coordinate transformation
401
         pollon=-180.
402
         pollat=90.+rotation
403
         rlon(i)=90.+lmtolms(rlat1(i),rlon1(i)-90.,pollat,pollon)
404
         rlat(i)=phtophs(rlat1(i),rlon1(i)-90.,pollat,pollon)   
405
 
406
      enddo
407
 
408
      END   
409
 
410
c     --------------------------------------------------------------------------------
411
c     Backward coordinate transformation (Rotated lon/lat -> True lon/lat)
412
c     --------------------------------------------------------------------------------
413
 
414
      SUBROUTINE getenvir_b (clon,clat,rotation,
415
     >                       lon,lat,rlon,rlat,n)
416
 
417
      implicit none
418
 
419
c     Declaration of input and output parameters
420
      integer     n
421
      real        clon,clat,rotation
422
      real        lon(n), lat(n)
423
      real        rlon(n),rlat(n)
424
 
425
c     Auxiliary variables 
426
      real         pollon,pollat
427
      integer      i
428
      real         rlon1(n),rlat1(n)
429
 
430
c     Externals
431
      real         lmstolm,phstoph
432
      external     lmstolm,phstoph
433
 
434
c     First coordinate transformation (make the local coordinate system parallel to equator)
435
      pollon=-180.
436
      pollat=90.+rotation
437
      do i=1,n
438
         rlon1(i)=90.+lmstolm(rlat(i),rlon(i)-90.,pollat,pollon)
439
         rlat1(i)=phstoph(rlat(i),rlon(i)-90.,pollat,pollon)            
440
      enddo
441
 
442
c     Second coordinate transformation (make the local coordinate system parallel to equator)
443
      pollon=clon-180.
444
      if (pollon.lt.-180.) pollon=pollon+360.
445
      pollat=90.-clat
446
      do i=1,n
447
         lon(i)=lmstolm(rlat1(i),rlon1(i),pollat,pollon)
448
         lat(i)=phstoph(rlat1(i),rlon1(i),pollat,pollon)            
449
      enddo
450
 
451
      END
452
 
453
c     --------------------------------------------------------------------------------
454
c     Transformation routine: LMSTOLM and PHSTOPH from library gm2em
455
c     --------------------------------------------------------------------------------
456
 
457
      REAL FUNCTION LMSTOLM (PHIS, LAMS, POLPHI, POLLAM)
458
C
459
C**** LMSTOLM  -   FC:BERECHNUNG DER WAHREN GEOGRAPHISCHEN LAENGE FUER
460
C****                 EINEN PUNKT MIT DEN KOORDINATEN (PHIS, LAMS)
461
C****                 IM ROTIERTEN SYSTEM. DER NORDPOL DES SYSTEMS HAT
462
C****                 DIE WAHREN KOORDINATEN (POLPHI, POLLAM)
463
C**   AUFRUF   :   LAM = LMSTOLM (PHIS, LAMS, POLPHI, POLLAM)
464
C**   ENTRIES  :   KEINE
465
C**   ZWECK    :   BERECHNUNG DER WAHREN GEOGRAPHISCHEN LAENGE FUER
466
C**                EINEN PUNKT MIT DEN KOORDINATEN (PHIS, LAMS)
467
C**                IM ROTIERTEN SYSTEM. DER NORDPOL DIESES SYSTEMS HAT
468
C**                DIE WAHREN KOORDINATEN (POLPHI, POLLAM)
469
C**   VERSIONS-
470
C**   DATUM    :   03.05.90
471
C**
472
C**   EXTERNALS:   KEINE
473
C**   EINGABE-
474
C**   PARAMETER:   PHIS     REAL   GEOGR. BREITE DES PUNKTES IM ROT.SYS.
475
C**                LAMS     REAL   GEOGR. LAENGE DES PUNKTES IM ROT.SYS.
476
C**                POLPHI   REAL   WAHRE GEOGR. BREITE DES NORDPOLS
477
C**                POLLAM   REAL   WAHRE GEOGR. LAENGE DES NORDPOLS
478
C**   AUSGABE-
479
C**   PARAMETER:   WAHRE GEOGRAPHISCHE LAENGE ALS WERT DER FUNKTION
480
C**                ALLE WINKEL IN GRAD (NORDEN>0, OSTEN>0)
481
C**
482
C**   COMMON-
483
C**   BLOECKE  :   KEINE
484
C**
485
C**   FEHLERBE-
486
C**   HANDLUNG :   KEINE
487
C**   VERFASSER:   D.MAJEWSKI
488
 
489
      REAL        LAMS,PHIS,POLPHI,POLLAM
490
 
491
      DATA        ZRPI18 , ZPIR18  / 57.2957795 , 0.0174532925 /
492
 
493
      ZSINPOL = SIN(ZPIR18*POLPHI)
494
      ZCOSPOL = COS(ZPIR18*POLPHI)
495
      ZLAMPOL = ZPIR18*POLLAM
496
      ZPHIS   = ZPIR18*PHIS
497
      ZLAMS   = LAMS
498
      IF(ZLAMS.GT.180.0) ZLAMS = ZLAMS - 360.0
499
      ZLAMS   = ZPIR18*ZLAMS
500
 
501
      ZARG1   = SIN(ZLAMPOL)*(- ZSINPOL*COS(ZLAMS)*COS(ZPHIS)  +
502
     1                          ZCOSPOL*           SIN(ZPHIS)) -
503
     2          COS(ZLAMPOL)*           SIN(ZLAMS)*COS(ZPHIS)
504
      ZARG2   = COS(ZLAMPOL)*(- ZSINPOL*COS(ZLAMS)*COS(ZPHIS)  +
505
     1                          ZCOSPOL*           SIN(ZPHIS)) +
506
     2          SIN(ZLAMPOL)*           SIN(ZLAMS)*COS(ZPHIS)
507
      IF (ABS(ZARG2).LT.1.E-30) THEN
508
        IF (ABS(ZARG1).LT.1.E-30) THEN
509
          LMSTOLM =   0.0
510
        ELSEIF (ZARG1.GT.0.) THEN
511
              LMSTOLAM =  90.0
512
            ELSE
513
              LMSTOLAM = -90.0
514
            ENDIF
515
      ELSE
516
        LMSTOLM = ZRPI18*ATAN2(ZARG1,ZARG2)
517
      ENDIF
518
 
519
      RETURN
520
      END
521
 
522
      REAL FUNCTION PHSTOPH (PHIS, LAMS, POLPHI, POLLAM)
523
C
524
C**** PHSTOPH  -   FC:BERECHNUNG DER WAHREN GEOGRAPHISCHEN BREITE FUER
525
C****                 EINEN PUNKT MIT DEN KOORDINATEN (PHIS, LAMS) IM
526
C****                 ROTIERTEN SYSTEM. DER NORDPOL DIESES SYSTEMS HAT
527
C****                 DIE WAHREN KOORDINATEN (POLPHI, POLLAM)
528
C**   AUFRUF   :   PHI = PHSTOPH (PHIS, LAMS, POLPHI, POLLAM)
529
C**   ENTRIES  :   KEINE
530
C**   ZWECK    :   BERECHNUNG DER WAHREN GEOGRAPHISCHEN BREITE FUER
531
C**                EINEN PUNKT MIT DEN KOORDINATEN (PHIS, LAMS) IM
532
C**                ROTIERTEN SYSTEM. DER NORDPOL DIESES SYSTEMS HAT
533
C**                DIE WAHREN KOORDINATEN (POLPHI, POLLAM)
534
C**   VERSIONS-
535
C**   DATUM    :   03.05.90
536
C**
537
C**   EXTERNALS:   KEINE
538
C**   EINGABE-
539
C**   PARAMETER:   PHIS     REAL   GEOGR. BREITE DES PUNKTES IM ROT.SYS.
540
C**                LAMS     REAL   GEOGR. LAENGE DES PUNKTES IM ROT.SYS.
541
C**                POLPHI   REAL   WAHRE GEOGR. BREITE DES NORDPOLS
542
C**                POLLAM   REAL   WAHRE GEOGR. LAENGE DES NORDPOLS
543
C**   AUSGABE-
544
C**   PARAMETER:   WAHRE GEOGRAPHISCHE BREITE ALS WERT DER FUNKTION
545
C**                ALLE WINKEL IN GRAD (NORDEN>0, OSTEN>0)
546
C**
547
C**   COMMON-
548
C**   BLOECKE  :   KEINE
549
C**
550
C**   FEHLERBE-
551
C**   HANDLUNG :   KEINE
552
C**   VERFASSER:   D.MAJEWSKI
553
 
554
      REAL        LAMS,PHIS,POLPHI,POLLAM
555
 
556
      DATA        ZRPI18 , ZPIR18  / 57.2957795 , 0.0174532925 /
557
 
558
      SINPOL = SIN(ZPIR18*POLPHI)
559
      COSPOL = COS(ZPIR18*POLPHI)
560
      ZPHIS  = ZPIR18*PHIS
561
      ZLAMS  = LAMS
562
      IF(ZLAMS.GT.180.0) ZLAMS = ZLAMS - 360.0
563
      ZLAMS  = ZPIR18*ZLAMS
564
      ARG     = COSPOL*COS(ZPHIS)*COS(ZLAMS) + SINPOL*SIN(ZPHIS)
565
 
566
      PHSTOPH = ZRPI18*ASIN(ARG)
567
 
568
      RETURN
569
      END
570
 
571
      REAL FUNCTION LMTOLMS (PHI, LAM, POLPHI, POLLAM)
572
C
573
C%Z% Modul %M%, V%I% vom %G%, extrahiert am %H%
574
C
575
C**** LMTOLMS  -   FC:UMRECHNUNG DER WAHREN GEOGRAPHISCHEN LAENGE LAM
576
C****                 AUF EINEM PUNKT MIT DEN KOORDINATEN (PHIS, LAMS)
577
C****                 IM ROTIERTEN SYSTEM. DER NORDPOL DES SYSTEMS HAT
578
C****                 DIE WAHREN KOORDINATEN (POLPHI, POLLAM)
579
C**   AUFRUF   :   LAM = LMTOLMS (PHI, LAM, POLPHI, POLLAM)
580
C**   ENTRIES  :   KEINE
581
C**   ZWECK    :   UMRECHNUNG DER WAHREN GEOGRAPHISCHEN LAENGE LAM AUF
582
C**                EINEM PUNKT MIT DEN KOORDINATEN (PHIS, LAMS) IM
583
C**                ROTIERTEN SYSTEM. DER NORDPOL DIESES SYSTEMS HAT
584
C**                DIE WAHREN KOORDINATEN (POLPHI, POLLAM)
585
C**   VERSIONS-
586
C**   DATUM    :   03.05.90
587
C**
588
C**   EXTERNALS:   KEINE
589
C**   EINGABE-
590
C**   PARAMETER:   PHI    REAL BREITE DES PUNKTES IM GEOGR. SYSTEM
591
C**                LAM    REAL LAENGE DES PUNKTES IM GEOGR. SYSTEM
592
C**                POLPHI REAL GEOGR.BREITE DES N-POLS DES ROT. SYSTEMS
593
C**                POLLAM REAL GEOGR.LAENGE DES N-POLS DES ROT. SYSTEMS
594
C**   AUSGABE-
595
C**   PARAMETER:   WAHRE GEOGRAPHISCHE LAENGE ALS WERT DER FUNKTION
596
C**                ALLE WINKEL IN GRAD (NORDEN>0, OSTEN>0)
597
C**
598
C**   COMMON-
599
C**   BLOECKE  :   KEINE
600
C**
601
C**   FEHLERBE-
602
C**   HANDLUNG :   KEINE
603
C**   VERFASSER:   G. DE MORSIER
604
 
605
      REAL        LAM,PHI,POLPHI,POLLAM
606
 
607
      DATA        ZRPI18 , ZPIR18  / 57.2957795 , 0.0174532925 /
608
 
609
      ZSINPOL = SIN(ZPIR18*POLPHI)
610
      ZCOSPOL = COS(ZPIR18*POLPHI)
611
      ZLAMPOL =     ZPIR18*POLLAM
612
      ZPHI    =     ZPIR18*PHI
613
      ZLAM    = LAM
614
      IF(ZLAM.GT.180.0) ZLAM = ZLAM - 360.0
615
      ZLAM    = ZPIR18*ZLAM
616
 
617
      ZARG1   = - SIN(ZLAM-ZLAMPOL)*COS(ZPHI)
618
      ZARG2   = - ZSINPOL*COS(ZPHI)*COS(ZLAM-ZLAMPOL)+ZCOSPOL*SIN(ZPHI)
619
      IF (ABS(ZARG2).LT.1.E-30) THEN
620
        IF (ABS(ZARG1).LT.1.E-30) THEN
621
          LMTOLMS =   0.0
622
        ELSEIF (ZARG1.GT.0.) THEN
623
              LMTOLMS =  90.0
624
            ELSE
625
              LMTOLMS = -90.0
626
            ENDIF
627
      ELSE
628
        LMTOLMS = ZRPI18*ATAN2(ZARG1,ZARG2)
629
      ENDIF
630
 
631
      RETURN
632
      END
633
 
634
      REAL FUNCTION PHTOPHS (PHI, LAM, POLPHI, POLLAM)
635
C
636
C%Z% Modul %M%, V%I% vom %G%, extrahiert am %H%
637
C
638
C**** PHTOPHS  -   FC:UMRECHNUNG DER WAHREN GEOGRAPHISCHEN BREITE PHI
639
C****                 AUF EINEM PUNKT MIT DEN KOORDINATEN (PHIS, LAMS)
640
C****                 IM ROTIERTEN SYSTEM. DER NORDPOL DES SYSTEMS HAT
641
C****                 DIE WAHREN KOORDINATEN (POLPHI, POLLAM)
642
C**   AUFRUF   :   PHI = PHTOPHS (PHI, LAM, POLPHI, POLLAM)
643
C**   ENTRIES  :   KEINE
644
C**   ZWECK    :   UMRECHNUNG DER WAHREN GEOGRAPHISCHEN BREITE PHI AUF
645
C**                EINEM PUNKT MIT DEN KOORDINATEN (PHIS, LAMS) IM
646
C**                ROTIERTEN SYSTEM. DER NORDPOL DIESES SYSTEMS HAT
647
C**                DIE WAHREN KOORDINATEN (POLPHI, POLLAM)
648
C**   VERSIONS-
649
C**   DATUM    :   03.05.90
650
C**
651
C**   EXTERNALS:   KEINE
652
C**   EINGABE-
653
C**   PARAMETER:   PHI    REAL BREITE DES PUNKTES IM GEOGR. SYSTEM
654
C**                LAM    REAL LAENGE DES PUNKTES IM GEOGR. SYSTEM
655
C**                POLPHI REAL GEOGR.BREITE DES N-POLS DES ROT. SYSTEMS
656
C**                POLLAM REAL GEOGR.LAENGE DES N-POLS DES ROT. SYSTEMS
657
C**   AUSGABE-
658
C**   PARAMETER:   ROTIERTE BREITE PHIS ALS WERT DER FUNKTION
659
C**                ALLE WINKEL IN GRAD (NORDEN>0, OSTEN>0)
660
C**
661
C**   COMMON-
662
C**   BLOECKE  :   KEINE
663
C**
664
C**   FEHLERBE-
665
C**   HANDLUNG :   KEINE
666
C**   VERFASSER:   G. DE MORSIER
667
 
668
      REAL        LAM,PHI,POLPHI,POLLAM
669
 
670
      DATA        ZRPI18 , ZPIR18  / 57.2957795 , 0.0174532925 /
671
 
672
      ZSINPOL = SIN(ZPIR18*POLPHI)
673
      ZCOSPOL = COS(ZPIR18*POLPHI)
674
      ZLAMPOL = ZPIR18*POLLAM
675
      ZPHI    = ZPIR18*PHI
676
      ZLAM    = LAM
677
      IF(ZLAM.GT.180.0) ZLAM = ZLAM - 360.0
678
      ZLAM    = ZPIR18*ZLAM
679
      ZARG    = ZCOSPOL*COS(ZPHI)*COS(ZLAM-ZLAMPOL) + ZSINPOL*SIN(ZPHI)
680
 
681
      PHTOPHS = ZRPI18*ASIN(ZARG)
682
 
683
      RETURN
684
      END
685
 
686
c     --------------------------------------------------------------------
687
c     Subroutines to write the netcdf output file
688
c     --------------------------------------------------------------------
689
 
690
      subroutine writecdf2D(cdfname,
691
     >                      varname,arr,time,
692
     >                      dx,dy,xmin,ymin,nx,ny,
693
     >                      crefile,crevar)
694
 
695
c     Create and write to the netcdf file <cdfname>. The variable
696
c     with name <varname> and with time <time> is written. The data
697
c     are in the two-dimensional array <arr>. The list <dx,dy,xmin,
698
c     ymin,nx,ny> specifies the output grid. The flags <crefile> and
699
c     <crevar> determine whether the file and/or the variable should
700
c     be created
701
 
702
      IMPLICIT NONE
703
 
704
c     Declaration of input parameters
705
      character*80 cdfname,varname
706
      integer nx,ny
707
      real arr(nx,ny)
708
      real dx,dy,xmin,ymin
709
      real time
710
      integer crefile,crevar
711
 
712
c     Further variables
713
      real varmin(4),varmax(4),stag(4)
714
      integer ierr,cdfid,ndim,vardim(4)
715
      character*80 cstname
716
      real mdv
717
      integer datar(14),stdate(5)
718
      integer i
719
 
720
C     Definitions
721
      varmin(1)=xmin
722
      varmin(2)=ymin
723
      varmin(3)=1050.
724
      varmax(1)=xmin+real(nx-1)*dx
725
      varmax(2)=ymin+real(ny-1)*dy
726
      varmax(3)=1050.
727
      cstname=trim(cdfname)//'_cst'
728
      ndim=4
729
      vardim(1)=nx
730
      vardim(2)=ny
731
      vardim(3)=1
732
      stag(1)=0.
733
      stag(2)=0.
734
      stag(3)=0.
735
      mdv=-999.98999
736
 
737
C     Create the file
738
      if (crefile.eq.0) then
739
         call cdfwopn(cdfname,cdfid,ierr)
740
         if (ierr.ne.0) goto 906
741
      else if (crefile.eq.1) then
742
         call crecdf(cdfname,cdfid,
743
     >        varmin,varmax,ndim,cstname,ierr)
744
         if (ierr.ne.0) goto 903
745
 
746
C        Write the constants file
747
         datar(1)=vardim(1)
748
         datar(2)=vardim(2)
749
         datar(3)=int(1000.*varmax(2))
750
         datar(4)=int(1000.*varmin(1))
751
         datar(5)=int(1000.*varmin(2))
752
         datar(6)=int(1000.*varmax(1))
753
         datar(7)=int(1000.*dx)
754
         datar(8)=int(1000.*dy)
755
         datar(9)=1
756
         datar(10)=1
757
         datar(11)=0            ! data version
758
         datar(12)=0            ! cstfile version
759
         datar(13)=0            ! longitude of pole
760
         datar(14)=90000        ! latitude of pole
761
         do i=1,5
762
            stdate(i)=0
763
         enddo
764
c         call wricst(cstname,datar,0.,0.,0.,0.,stdate)
765
      endif
766
 
767
c     Write the data to the netcdf file, and close the file
768
      if (crevar.eq.1) then
769
         call putdef(cdfid,varname,ndim,mdv,
770
     >        vardim,varmin,varmax,stag,ierr)
771
         if (ierr.ne.0) goto 904
772
      endif
773
      call putdat(cdfid,varname,time,0,arr,ierr)
774
      if (ierr.ne.0) goto 905
775
      call clscdf(cdfid,ierr)
776
 
777
      return
778
 
779
c     Error handling
780
 903  print*,'*** Problem to create netcdf file ***'
781
      stop
782
 904  print*,'*** Problem to write definition ***'
783
      stop
784
 905  print*,'*** Problem to write data ***'
785
      stop
786
 906  print*,'*** Problem to open netcdf file ***'
787
      stop
788
 
789
      END
790
 
791
 
792