ABOUT ME

-

Today
-
Yesterday
-
Total
-
  • [Python] datetime timezone 변경방법
    언어/파이썬 & 장고 2017. 10. 16. 19:13

    python 3.6 이하 버전에서는 datetime을 생성하면 timezone 정보가 없어 astimezone 같은 메소드를 실행하면 에러가 발생합니다. 지금부터 삽질해서 찾은 방법을 설명합니다. 


    python 3.6은 datetime을 생성할 때 timezone을 지정하지 않아도 기본으로 내장으로 설정이 되어 있어 astimezone()를 실행해도 에러가 발생하지 않습니다. 하지만 3.6이하 버전은 datetime을 생성할 때 timezone을 지정하지 않으면 timezone이 None이므로 astimezone()을 실행하면 에러가 발생합니다. 따라서 결론은 datetime을 생성할 때 timezone을 지정하는 것입니다.


    하지만 이미 생성된 datetime이라면 어떨까..

    여기서 방법은 2가지로 나뉩니다.

    datetime → time → datetime 으로 변환

    먼저 datetime을 time타입으로 변환 시킨 다음, 이 값으로 timezone을 지정하여 datetime객체를 새로 생성하는 방법입니다.

    이 방법은 아래에서 설명할 replace()함수가 지원되지 않는 python 버전에서 사용할 수 있습니다.

    import datetime
    import time
    
    now_dt = datetime.datetime.now()
    print(now_dt)
    
    now_t = time.mktime(now_dt.timetuple()) + now_dt.microsecond / 1E6
    
    print(now_t)
    
    c_now_dt = datetime.datetime.fromtimestamp(now_t, datetime.timezone.utc)
    print(c_now_dt)
    
    # 결과
    # 2017-10-15 18:45:32.357988
    # 1508060732.357988
    # 2017-10-15 09:45:32.357988+00:00

    replace() 사용 (pyhton 3.3 이상)

    위 방법은 상당히 귀찮으므로 python 버전이 3.3 이상이면 replace()함수를 사용합니다.

    import datetime
    
    
    now_dt = datetime.datetime.now()
    print(now_dt)
    
    c_now_dt = now_dt.replace(tzinfo=datetime.timezone.utc)
    print(c_now_dt)
    
    # 결과
    # 2017-10-15 18:48:32.402106
    # 2017-10-15 18:48:32.402106+00:00

    주의점

    위 두 결과를 보고 확인이 되듯이 replace()함수를 사용해 timezone을 입력하면 timezone은 변경이 되지만 utc 시간대로 변경되지 않습니다(!!)

    아래는 python 3.6대에서 astimezone()도 추가하여 비교한 코드입니다.

    import datetime
    import time
    
    now_dt = datetime.datetime.now()
    print('현재 시간: ', now_dt)
    
    now_t = time.mktime(now_dt.timetuple()) + now_dt.microsecond / 1E6
    c_now_dt = datetime.datetime.fromtimestamp(now_t, datetime.timezone.utc)
    
    print('datetime-> time -> datetime 변환시간: ', c_now_dt)
    
    print('replace() 변환시간: ',now_dt.replace(tzinfo=datetime.timezone.utc))
    print('astimezone() 변환시간: ',now_dt.astimezone(datetime.timezone.utc))
    
    
    # 현재 시간:  2017-10-16 19:09:44.162545
    # datetime-> time -> datetime 변환시간:  2017-10-16 10:09:44.162545+00:00
    # replace() 변환시간:  2017-10-16 19:09:44.162545+00:00
    # astimezone() 변환시간:  2017-10-16 10:09:44.162545+00:00


    이것처럼 replace()를 사용할 때, utc 시간대로 변경되지 않는 다는 점을 숙지하고 사용해야 합니다.

    결론

    datetime 생성할떄 timezone과 timedeltal를 이용해서 필요한 타임존 설정을 해주면 모든게 해결됨. (근데 귀찮다)

    댓글