source: trunk/WRF.COMMON/WRFV2/external/esmf_time_f90/ESMF_BaseTime.F90

Last change on this file was 11, checked in by aslmd, 14 years ago

spiga@svn-planeto:ajoute le modele meso-echelle martien

File size: 11.4 KB
Line 
1!
2! Earth System Modeling Framework
3! Copyright 2002-2003, University Corporation for Atmospheric Research,
4! Massachusetts Institute of Technology, Geophysical Fluid Dynamics
5! Laboratory, University of Michigan, National Centers for Environmental
6! Prediction, Los Alamos National Laboratory, Argonne National Laboratory,
7! NASA Goddard Space Flight Center.
8! Licensed under the GPL.
9!
10!==============================================================================
11!
12!     ESMF BaseTime Module
13      module ESMF_BaseTimeMod
14!
15!==============================================================================
16!
17! This file contains the BaseTime class definition and all BaseTime class
18! methods.
19!
20!------------------------------------------------------------------------------
21! INCLUDES
22
23#include <ESMF_TimeMgr.inc>
24!
25!===============================================================================
26!BOPI
27! !MODULE: ESMF_BaseTimeMod - Base ESMF time definition
28!
29! !DESCRIPTION:
30! Part of Time Manager F90 API wrapper of C++ implemenation
31!
32! This module serves only as the common Time definition inherited
33! by {\tt ESMF\_TimeInterval} and {\tt ESMF\_Time}
34!
35! See {\tt ../include/ESMC\_BaseTime.h} for complete description
36!
37!------------------------------------------------------------------------------
38! !USES:
39      use ESMF_BaseMod    ! ESMF Base class
40      implicit none
41!
42!------------------------------------------------------------------------------
43! !PRIVATE TYPES:
44      private
45!------------------------------------------------------------------------------
46!     ! ESMF_BaseTime
47!
48!     ! Base class type to match C++ BaseTime class in size only;
49!     !  all dereferencing within class is performed by C++ implementation
50
51      type ESMF_BaseTime
52        integer(ESMF_KIND_I8) :: S   ! whole seconds
53        integer(ESMF_KIND_I8) :: Sn  ! fractional seconds, numerator
54        integer(ESMF_KIND_I8) :: Sd  ! fractional seconds, denominator
55      end type
56
57!------------------------------------------------------------------------------
58! !PUBLIC TYPES:
59      public ESMF_BaseTime
60!------------------------------------------------------------------------------
61!
62! !PUBLIC MEMBER FUNCTIONS:
63!
64! overloaded operators
65      public operator(+)
66      private ESMF_BaseTimeSum
67      public operator(-)
68      private ESMF_BaseTimeDifference
69      public operator(/)
70      private ESMF_BaseTimeQuotI
71      private ESMF_BaseTimeQuotI8
72      public operator(.EQ.)
73      private ESMF_BaseTimeEQ
74      public operator(.NE.)
75      private ESMF_BaseTimeNE
76      public operator(.LT.)
77      private ESMF_BaseTimeLT
78      public operator(.GT.)
79      private ESMF_BaseTimeGT
80      public operator(.LE.)
81      private ESMF_BaseTimeLE
82      public operator(.GE.)
83      private ESMF_BaseTimeGE
84
85!==============================================================================
86!
87! INTERFACE BLOCKS
88!
89!==============================================================================
90      interface operator(+)
91        module procedure ESMF_BaseTimeSum
92      end interface
93      interface operator(-)
94        module procedure ESMF_BaseTimeDifference
95      end interface
96      interface operator(/)
97        module procedure ESMF_BaseTimeQuotI,ESMF_BaseTimeQuotI8
98      end interface
99      interface operator(.EQ.)
100        module procedure ESMF_BaseTimeEQ
101      end interface
102      interface operator(.NE.)
103        module procedure ESMF_BaseTimeNE
104      end interface
105      interface operator(.LT.)
106        module procedure ESMF_BaseTimeLT
107      end interface
108      interface operator(.GT.)
109        module procedure ESMF_BaseTimeGT
110      end interface
111      interface operator(.LE.)
112        module procedure ESMF_BaseTimeLE
113      end interface
114      interface operator(.GE.)
115        module procedure ESMF_BaseTimeGE
116      end interface
117
118
119!==============================================================================
120
121      contains
122
123!==============================================================================
124
125
126! Add two basetimes
127      FUNCTION ESMF_BaseTimeSum( basetime1, basetime2 )
128        TYPE(ESMF_BaseTime) :: ESMF_BaseTimeSum
129        TYPE(ESMF_BaseTime), INTENT(IN) :: basetime1
130        TYPE(ESMF_BaseTime), INTENT(IN) :: basetime2
131        ! locals
132        INTEGER (ESMF_KIND_I8) :: Sn1, Sd1, Sn2, Sd2, lcd
133!  PRINT *,'DEBUG:  BEGIN ESMF_BaseTimeSum()'
134!  PRINT *,'DEBUG:  ESMF_BaseTimeSum():  basetime1%S = ',basetime1%S
135!  PRINT *,'DEBUG:  ESMF_BaseTimeSum():  basetime1%Sn = ',basetime1%Sn
136!  PRINT *,'DEBUG:  ESMF_BaseTimeSum():  basetime1%Sd = ',basetime1%Sd
137!  PRINT *,'DEBUG:  ESMF_BaseTimeSum():  basetime2%S = ',basetime2%S
138!  PRINT *,'DEBUG:  ESMF_BaseTimeSum():  basetime2%Sn = ',basetime2%Sn
139!  PRINT *,'DEBUG:  ESMF_BaseTimeSum():  basetime2%Sd = ',basetime2%Sd
140        ESMF_BaseTimeSum   = basetime1
141        ESMF_BaseTimeSum%S = ESMF_BaseTimeSum%S + basetime2%S
142        Sn1 = basetime1%Sn
143        Sd1 = basetime1%Sd
144        Sn2 = basetime2%Sn
145        Sd2 = basetime2%Sd
146!  PRINT *,'DEBUG:  ESMF_BaseTimeSum():  Sn1 = ',Sn1
147!  PRINT *,'DEBUG:  ESMF_BaseTimeSum():  Sd1 = ',Sd1
148!  PRINT *,'DEBUG:  ESMF_BaseTimeSum():  Sn2 = ',Sn2
149!  PRINT *,'DEBUG:  ESMF_BaseTimeSum():  Sd2 = ',Sd2
150        IF      ( ( Sd1 .EQ. 0 ) .AND. ( Sd2 .EQ. 0 ) ) THEN
151!  PRINT *,'DEBUG:  ESMF_BaseTimeSum():  no fractions'
152          ESMF_BaseTimeSum%Sn = 0
153          ESMF_BaseTimeSum%Sd = 0
154        ELSE IF ( ( Sd1 .NE. 0 ) .AND. ( Sd2 .EQ. 0 ) ) THEN
155          ESMF_BaseTimeSum%Sn = Sn1
156          ESMF_BaseTimeSum%Sd = Sd1
157        ELSE IF ( ( Sd1 .EQ. 0 ) .AND. ( Sd2 .NE. 0 ) ) THEN
158          ESMF_BaseTimeSum%Sn = Sn2
159          ESMF_BaseTimeSum%Sd = Sd2
160        ELSE IF ( ( Sd1 .NE. 0 ) .AND. ( Sd2 .NE. 0 ) ) THEN
161          CALL compute_lcd( Sd1 , Sd2 , lcd )
162          ESMF_BaseTimeSum%Sd = lcd
163          ESMF_BaseTimeSum%Sn = (Sn1 * lcd / Sd1) + (Sn2 * lcd / Sd2)
164        ENDIF
165!  PRINT *,'DEBUG:  ESMF_BaseTimeSum():  ESMF_BaseTimeSum%S = ',ESMF_BaseTimeSum%S
166!  PRINT *,'DEBUG:  ESMF_BaseTimeSum():  ESMF_BaseTimeSum%Sn = ',ESMF_BaseTimeSum%Sn
167!  PRINT *,'DEBUG:  ESMF_BaseTimeSum():  ESMF_BaseTimeSum%Sd = ',ESMF_BaseTimeSum%Sd
168        CALL normalize_basetime( ESMF_BaseTimeSum )
169!  PRINT *,'DEBUG:  END ESMF_BaseTimeSum()'
170      END FUNCTION ESMF_BaseTimeSum
171
172
173! Subtract two basetimes
174      FUNCTION ESMF_BaseTimeDifference( basetime1, basetime2 )
175        TYPE(ESMF_BaseTime) :: ESMF_BaseTimeDifference
176        TYPE(ESMF_BaseTime), INTENT(IN) :: basetime1
177        TYPE(ESMF_BaseTime), INTENT(IN) :: basetime2
178        ! locals
179        TYPE(ESMF_BaseTime) :: neg2
180
181        neg2%S  = -basetime2%S
182        neg2%Sn = -basetime2%Sn
183        neg2%Sd =  basetime2%Sd
184
185        ESMF_BaseTimeDifference = basetime1 + neg2
186
187      END FUNCTION ESMF_BaseTimeDifference
188
189
190! Divide basetime by 8-byte integer
191      FUNCTION ESMF_BaseTimeQuotI8( basetime, divisor )
192        TYPE(ESMF_BaseTime) :: ESMF_BaseTimeQuotI8
193        TYPE(ESMF_BaseTime), INTENT(IN) :: basetime
194        INTEGER(ESMF_KIND_I8), INTENT(IN) :: divisor
195        ! locals
196        INTEGER(ESMF_KIND_I8) :: d, n, dinit
197
198!PRINT *,'DEBUG ESMF_BaseTimeQuotI8() A:  S,Sn,Sd = ', &
199!  basetime%S,basetime%Sn,basetime%Sd
200!PRINT *,'DEBUG ESMF_BaseTimeQuotI8() A:  divisor = ', divisor
201        IF ( divisor == 0_ESMF_KIND_I8 ) THEN
202          CALL wrf_error_fatal( 'ESMF_BaseTimeQuotI8:  divide by zero' )
203        ENDIF
204
205!$$$ move to default constructor
206        ESMF_BaseTimeQuotI8%S  = 0
207        ESMF_BaseTimeQuotI8%Sn = 0
208        ESMF_BaseTimeQuotI8%Sd = 0
209
210        ! convert to a fraction and divide by multipling the denonminator by
211        ! the divisor
212        IF ( basetime%Sd == 0 ) THEN
213          dinit = 1_ESMF_KIND_I8
214        ELSE
215          dinit = basetime%Sd
216        ENDIF
217        n = basetime%S * dinit + basetime%Sn
218        d = dinit * divisor
219!PRINT *,'DEBUG ESMF_BaseTimeQuotI8() B:  n,d = ',n,d
220        CALL simplify( n, d, ESMF_BaseTimeQuotI8%Sn, ESMF_BaseTimeQuotI8%Sd )
221!PRINT *,'DEBUG ESMF_BaseTimeQuotI8() C:  S,Sn,Sd = ', &
222!  ESMF_BaseTimeQuotI8%S,ESMF_BaseTimeQuotI8%Sn,ESMF_BaseTimeQuotI8%Sd
223        CALL normalize_basetime( ESMF_BaseTimeQuotI8 )
224!PRINT *,'DEBUG ESMF_BaseTimeQuotI8() D:  S,Sn,Sd = ', &
225!  ESMF_BaseTimeQuotI8%S,ESMF_BaseTimeQuotI8%Sn,ESMF_BaseTimeQuotI8%Sd
226      END FUNCTION ESMF_BaseTimeQuotI8
227
228! Divide basetime by integer
229      FUNCTION ESMF_BaseTimeQuotI( basetime, divisor )
230        TYPE(ESMF_BaseTime) :: ESMF_BaseTimeQuotI
231        TYPE(ESMF_BaseTime), INTENT(IN) :: basetime
232        INTEGER, INTENT(IN) :: divisor
233        IF ( divisor == 0 ) THEN
234          CALL wrf_error_fatal( 'ESMF_BaseTimeQuotI:  divide by zero' )
235        ENDIF
236        ESMF_BaseTimeQuotI = basetime / INT( divisor, ESMF_KIND_I8 )
237      END FUNCTION ESMF_BaseTimeQuotI
238
239
240! .EQ. for two basetimes
241      FUNCTION ESMF_BaseTimeEQ( basetime1, basetime2 )
242        LOGICAL :: ESMF_BaseTimeEQ
243        TYPE(ESMF_BaseTime), INTENT(IN) :: basetime1
244        TYPE(ESMF_BaseTime), INTENT(IN) :: basetime2
245        INTEGER :: retval
246        CALL seccmp( basetime1%S, basetime1%Sn, basetime1%Sd, &
247                     basetime2%S, basetime2%Sn, basetime2%Sd, &
248                     retval )
249        ESMF_BaseTimeEQ = ( retval .EQ. 0 )
250      END FUNCTION ESMF_BaseTimeEQ
251
252
253! .NE. for two basetimes
254      FUNCTION ESMF_BaseTimeNE( basetime1, basetime2 )
255        LOGICAL :: ESMF_BaseTimeNE
256        TYPE(ESMF_BaseTime), INTENT(IN) :: basetime1
257        TYPE(ESMF_BaseTime), INTENT(IN) :: basetime2
258        INTEGER :: retval
259        CALL seccmp( basetime1%S, basetime1%Sn, basetime1%Sd, &
260                     basetime2%S, basetime2%Sn, basetime2%Sd, &
261                     retval )
262        ESMF_BaseTimeNE = ( retval .NE. 0 )
263      END FUNCTION ESMF_BaseTimeNE
264
265
266! .LT. for two basetimes
267      FUNCTION ESMF_BaseTimeLT( basetime1, basetime2 )
268        LOGICAL :: ESMF_BaseTimeLT
269        TYPE(ESMF_BaseTime), INTENT(IN) :: basetime1
270        TYPE(ESMF_BaseTime), INTENT(IN) :: basetime2
271        INTEGER :: retval
272        CALL seccmp( basetime1%S, basetime1%Sn, basetime1%Sd, &
273                     basetime2%S, basetime2%Sn, basetime2%Sd, &
274                     retval )
275        ESMF_BaseTimeLT = ( retval .LT. 0 )
276      END FUNCTION ESMF_BaseTimeLT
277
278
279! .GT. for two basetimes
280      FUNCTION ESMF_BaseTimeGT( basetime1, basetime2 )
281        LOGICAL :: ESMF_BaseTimeGT
282        TYPE(ESMF_BaseTime), INTENT(IN) :: basetime1
283        TYPE(ESMF_BaseTime), INTENT(IN) :: basetime2
284        INTEGER :: retval
285        CALL seccmp( basetime1%S, basetime1%Sn, basetime1%Sd, &
286                     basetime2%S, basetime2%Sn, basetime2%Sd, &
287                     retval )
288        ESMF_BaseTimeGT = ( retval .GT. 0 )
289      END FUNCTION ESMF_BaseTimeGT
290
291
292! .LE. for two basetimes
293      FUNCTION ESMF_BaseTimeLE( basetime1, basetime2 )
294        LOGICAL :: ESMF_BaseTimeLE
295        TYPE(ESMF_BaseTime), INTENT(IN) :: basetime1
296        TYPE(ESMF_BaseTime), INTENT(IN) :: basetime2
297        INTEGER :: retval
298        CALL seccmp( basetime1%S, basetime1%Sn, basetime1%Sd, &
299                     basetime2%S, basetime2%Sn, basetime2%Sd, &
300                     retval )
301        ESMF_BaseTimeLE = ( retval .LE. 0 )
302      END FUNCTION ESMF_BaseTimeLE
303
304
305! .GE. for two basetimes
306      FUNCTION ESMF_BaseTimeGE( basetime1, basetime2 )
307        LOGICAL :: ESMF_BaseTimeGE
308        TYPE(ESMF_BaseTime), INTENT(IN) :: basetime1
309        TYPE(ESMF_BaseTime), INTENT(IN) :: basetime2
310        INTEGER :: retval
311        CALL seccmp( basetime1%S, basetime1%Sn, basetime1%Sd, &
312                     basetime2%S, basetime2%Sn, basetime2%Sd, &
313                     retval )
314        ESMF_BaseTimeGE = ( retval .GE. 0 )
315      END FUNCTION ESMF_BaseTimeGE
316
317
318      end module ESMF_BaseTimeMod
Note: See TracBrowser for help on using the repository browser.