반응형

     정보

    • 업무명     : 포트란 유닉스 시간 (Unix Time)을 날짜로 변환

    • 작성자     : 이상호

    • 작성일     : 2020-01-26

    • 설   명      :

    • 수정이력 :

     

     내용

    [개요]

    • 안녕하세요? 웹 개발 및 연구 개발을 담당하고 있는 해솔입니다.

    • 포트란 (Fortran)에서는 유닉스 시간을 다루기 위한 내장 함수를 제공하지 않습니다.

    • 따라서 유닉스 시간을 날짜로 변환 방법을 소개드리고자 합니다.

     

     

    [특징]

    • 다양한 기상 자료를 처리하기 위해서 유닉스 시간을 날짜로 변환 기술이 요구되며 이 프로그램은 이러한 목적을 달성하기 위한 소프트웨어

     

    [기능]

    • 유닉스 시간 변환

     

    [활용 자료]

    • 없음

     

    [자료 처리 방안 및 활용 분석 기법]

    • 없음

     

    [사용법]

    • 작업 환경 구축

    • 소스 코드 컴파일 (ifort *.f90) 

    • 소스 코드 실행 (./a.out)

    • 실행 결과 확인

     

    [사용 OS]

    • Linux (CentOS v7.0)

    • VMware Workstation Pro v15.5

     

    [사용 언어]

    • Fortran (ifort v19.1.0.166)

     

     내용

    [유닉스 시간]

    • 대부분 기상 자료의 경우 유닉스 시간에 따른 기상 정보가 포함되어 있습니다.

    • Fortran에서는 유닉스 시간에 대한 상호 변환 라이브러리를 제공하지 않기 때문에 상당한 어려움이 있습니다.

    • 여기서 유닉스 시간 (Unix Time)은 시간 표현 형식 중 하나로서 유닉스 에포크 시간 (Unix Epoch Time)이라고 말합니다.

    • 즉 협정 세계시 (UTC)의 경우 1970년 01월 01일 0시 0분 0초를 기준으로 경과 시간을 초로 환산하여 정수로 표현합니다. 한국 표준시 (KST)에서는 UTC를 기준으로 9시간 더하기 때문에 1970년 01월 01일 9시 0분 0초 기준으로 합니다.

    • 예를 들면 "현지 한국 시간 (2020년 01월 27일 23시 46분 06초)"를 기준으로 유닉스 시간은 "1580168766"을 의미합니다 (아래 표 참조). 

     

    현재 시간 2020-01-27 23:46:06
    Unix Time 1580168766
    날짜 표기 2020/01/27 23:46:06 
    구분자 (-) 표기 2020-01-27 23:46:06 
    구분자 없음 20200127 234606 
    한국 표준시 표기 2020년 01월 27일 월요일 23시 46분 06초
    ISO 8601 2020-01-27T23:46:06+09:00 
    RFC 2822 형식 Mon, 27 Jan 2020 23:46:06 +0900 

     

    [소스 코드]

    • 앞서 현지 시간을 기준으로 "Date2UnixTime 서브루틴"으로 유닉스 시간 변환

    • 유닉스 시간을 기준으로 "UnixTime2Date" 서브루틴"으로 날짜 변환

    • 정상적으로 처리 후에 "Convert Done" 메시지 출력

     

          program Convert_Unix_Time_To_Date
    
             implicit none
    
             integer :: iCount
             integer :: iYear = 0, iMonth = 0, iDay = 0, iHour = 0, iMunute = 0, iSec = 0
             
             call Date2UnixTime(2020, 1, 27, 23, 46, 06, iCount)
             write(*, '(a, g0)') "Unix Time : ", iCount
             
             call UnixTime2Date(iCount, iYear, iMonth, iDay, iHour, iMunute, iSec)
             write(*, *) "Date : ", iYear, iMonth, iDay, iHour, iMunute, iSec
          
             write(*, *) "Convert Done"
    
          end program Convert_Unix_Time_To_Date
          
          ! Convert UnixTime (Seconds since 1970) to Date and time  
          ! Range From 1970 to January 19, 2038 03:14:07
          subroutine UnixTime2Date(iUnixTime, iYear, iMonth, iDay, iHour, iMinute, iSec)
             
             implicit none
             integer, intent(in) :: iUnixTime
             integer, intent(out) :: iYear, iMonth, iDay, iHour, iMinute, iSec
             integer :: uDays, uSecs, mDay, n
             real :: rDay
    
             uDays = int(iUnixTime / 86400)
             uSecs = mod(iUnixTime, 86400)
             mDay = uDays + 40587
             iYear = 1858 + int((mDay + 321.51) / 365.25)
             rDay = aint(mod(mDay + 262.25, 365.25)) + 0.5
             iMonth  = 1 + int(mod(rDay / 30.6 + 2.0, 12.0))
             iDay  = 1 + int(mod(rDay,30.6))
             n    = uSecs
             iSec = mod(n, 60)
             n    = n / 60
             iMinute  = mod(n, 60)
             iHour  = n / 60
          end subroutine UnixTime2Date
          
          ! Convert Date and time to UnixTime (Seconds since 1970)
          ! Range From 1970 to January 19, 2038 03:14:07
          subroutine Date2UnixTime(iYear, iMonth, iDay, iHour, iMinute, iSec, iUnixTime)
       
             implicit none
             integer , intent(in) :: iYear, iMonth, iDay, iHour, iMinute, iSec
             integer , intent(out) :: iUnixTime
             integer :: iy , im
             integer :: a
             real :: jd
    
             if (iMonth > 2) then
                iy = iYear
                im = iMonth
             else
                iy = iYear - 1
                im = iMonth + 12
             end if
    
             a = INT(iy / 100)
             a = 2 - a + INT(a / 4)
             JD = INT(365.25 * (iy + 4716)) + INT(30.60001 * (im + 1)) + iDay + a -1524.5
             iUnixTime = Int( (JD - 2440587.5) * 86400) + (iHour * 3600) + (iMinute * 60) + iSec
          end subroutine Date2UnixTime

     

     

     참고 문헌

    [논문]

    • 없음

    [보고서]

    • 없음

    [URL]

    • 없음

     

     문의사항

    [기상학/프로그래밍 언어]

    • sangho.lee.1990@gmail.com

    [해양학/천문학/빅데이터]

    • saimang0804@gmail.com
    반응형
    • 네이버 블러그 공유하기
    • 네이버 밴드에 공유하기
    • 페이스북 공유하기
    • 카카오스토리 공유하기