Monday, September 26, 2011

COBOL - Gregorian Date to Julian

Do you know any easy ways (COBOL) to convert:

1. A Gregorian Date to Julian (20021231 ==> 2002365)
2. A Julian Date to Gregorian (2002365  ==> 20021231)


Solution 1


Here is the COBOL snippet which would serve the purpose.

IDENTIFICATION DIVISION.
PROGRAM-ID.  DATCONV.  
DATA DIVISION.

WORKING-STORAGE SECTION.                                  
01  WS-WORK-AREA.                                        
    05 MONTH-END-DD                  PIC  X(24)          
                VALUE '312831303130313130313031'.        
    05 TBL-MONTH-END         REDEFINES MONTH-END-DD.      
       10 TBL-MONTH-END-DAY  OCCURS    12 TIMES.          
          15 TBL-MONTH-END-DD        PIC  9(02).          
                                                         
    05 WS-GREG-DATE.                                      
       10 GYYY                       PIC  9(04).          
       10 MM                         PIC  9(02).        
       10 DD                         PIC  9(02).        

    05 WS-JULN-DATE.                                    
       10 JYYY                       PIC  9(04).        
       10 DOY                        PIC  9(03).        
    05 TEMP                          PIC  9(03).        
    05 I                             PIC  9(02).

PROCEDURE DIVISION.                                    
                                                       
0000-MAIN-PARA.        
** Gregorian to Julian **                                    
    ACCEPT WS-GREG-DATE                                      
    IF ( FUNCTION MOD ( GYYY, 400 ) = 0) OR          
       ( FUNCTION MOD ( GYYY, 4 ) = 0   AND          
         FUNCTION MOD ( GYYY, 100 ) NOT = 0 )        
       MOVE '29' TO MONTH-END-DD (3:2)              
    ELSE                                            
       MOVE '28' TO MONTH-END-DD (3:2)              
   END-IF
    MOVE GYYY                       TO JYYY                  
    MOVE DD                         TO DOY                  
    PERFORM ADD-MONTHDAYS                                    
        VARYING I FROM 1 BY 1                                
        UNTIL   I >= MM
    DISPLAY 'GREGORIAN DATE         : '  WS-GREG-DATE        
    DISPLAY 'JULIAN    DATE         : '  WS-JULN-DATE        

** Julian to Gregorian **                                    
    ACCEPT WS-JULN-DATE                                      
    IF ( FUNCTION MOD ( JYYY, 400 ) = 0) OR          
       ( FUNCTION MOD ( JYYY, 4 ) = 0   AND          
         FUNCTION MOD ( JYYY, 100 ) NOT = 0 )        
       MOVE '29' TO MONTH-END-DD (3:2)              
    ELSE                                            
       MOVE '28' TO MONTH-END-DD (3:2)              
   END-IF            
    MOVE JYYY                       TO GYYY                  
    MOVE DOY                        TO TEMP                  
    PERFORM SUB-MONTHDAYS                                    
        VARYING I FROM 1 BY 1                                
        UNTIL  TEMP <= TBL-MONTH-END-DD (I)            
    MOVE I                          TO MM              
    MOVE TEMP                       TO DD              
    DISPLAY 'JULIAN    DATE         : '  WS-JULN-DATE  
    DISPLAY 'GREGORIAN DATE         : '  WS-GREG-DATE  
                                                       
    STOP RUN.                                          
                                                       
ADD-MONTHDAYS.                                          
    ADD TBL-MONTH-END-DD (I)        TO DOY.            
                                                       
SUB-MONTHDAYS.                                          
    SUBTRACT TBL-MONTH-END-DD (I)   FROM TEMP. 



Solution 2


There is an easy way out also. It can be achieved by using COBOL intrinsic functions described below.

  FUNCTION                    Description
 ---------------             ---------------------------------------------
 DATE-OF-INTEGER          Gregorian date equivalent (YYYYMMDD) of integer date
 DAY-OF-INTEGER           Julian date equivalent (YYYYDDD) of integer date
 INTEGER-OF-DATE          Integer date equivalent of Gregorian date (YYYYMMDD)    
 INTEGER-OF-DAY           Integer date equivalent of Julian date(YYYYDDD)


  Here integer date is a seven-digit integer with a range from 1 to 3,067,671. (corresponding to dates ranging from January 1, 1601 through December 31, 9999).
  The Gregorian date is obtained from the calculation
               (YYYY * 10,000) + (MM * 100) + DD.
o   YYYY represents the year. It must be an integer greater than 1600, but not greater than 9999.    
o   MM represents a month and must be a positive integer less than 13.    
o   DD represents a day and must be a positive integer less than 32, provided that it is valid for the specified month and year combination.

 The returned value of INTEGER-OF-DATE/DAY functions is an integer that is the number of days the date represented by given input, succeeds December 31, 1600 in the Gregorian calendar.

  Here is the program....


IDENTIFICATION DIVISION.
PROGRAM-ID.  DDCONV.

 DATA DIVISION.                                  
                                                 
 WORKING-STORAGE SECTION.                        
 01 WS-WORK-AREA.                                
     05 WS-GREG-DATE                  PIC  9(08).
     05 WS-JULN-DATE                  PIC  9(07).
     05 WS-INT-DATE                   PIC  9(07).

 PROCEDURE DIVISION.                                          
                                                               
 0000-MAIN-PARA.                                              
     ACCEPT  WS-GREG-DATE                                      
** Gregorian To Julian **                                      
     COMPUTE WS-INT-DATE  = FUNCTION INTEGER-OF-DATE(WS-GREG-DATE)
     COMPUTE WS-JULN-DATE = FUNCTION DAY-OF-INTEGER(WS-INT-DATE)
     DISPLAY 'GREGORIAN DATE        : '  WS-GREG-DATE          
     DISPLAY 'JULIAN    DATE        : '  WS-JULN-DATE          
                                                               
     ACCEPT  WS-JULN-DATE                                      
** Julian To Gregorian **                                      
     COMPUTE WS-INT-DATE  = FUNCTION INTEGER-OF-DAY(WS-JULN-DATE)
     COMPUTE WS-GREG-DATE = FUNCTION DATE-OF-INTEGER(WS-INT-DAY)
     DISPLAY 'JULIAN    DATE        : '  WS-JULN-DATE          
     DISPLAY 'GREGORIAN DATE        : '  WS-GREG-DATE          

     STOP RUN.  


No comments:

Post a Comment

Note: Only a member of this blog may post a comment.