date는 달력 날짜, time은 시계 시각, datetime은 둘의 결합, timedelta는 두 시점 사이의 길이를 나타내.
시간대가 없는 값과 있는 값을 구분해
tzinfo가 없는 datetime과 있는 datetime은 산술에서 섞을 수 없어. 저장과 비교에는 UTC를 붙인 값을 쓰고, 사람에게 보여줄 때 ZoneInfo('Asia/Seoul') 같은 지역 시간대로 바꿔.
ISO 8601과 달력 계산
isoformat/fromisoformat은 오프셋을 포함해 모호하지 않은 왕복 문자열을 만들어. “24시간 뒤”와 “현지 시각으로 내일 같은 때”는 DST 경계에서 다를 수 있으니 기간과 달력 의도를 구분해.
Code
날짜와 시각 만들고 표시하기·python
from datetime import datetime, date, time, timedelta, timezone
from zoneinfo import ZoneInfo
# 오늘, 지금
print(date.today()) # 2026-05-02
print(datetime.now()) # naive — 안 좋음! 현대 코드에선 피해
print(datetime.now(timezone.utc)) # aware — 좋음
print(datetime.now(ZoneInfo("Asia/Seoul"))) # 서울 시간 aware
# 생성
dt = datetime(2026, 5, 2, 15, 30, tzinfo=ZoneInfo("Asia/Seoul"))
print(dt) # 2026-05-02 15:30:00+09:00
# ISO 포맷 — 현대 표준
print(dt.isoformat()) # 2026-05-02T15:30:00+09:00
print(datetime.fromisoformat("2026-05-02T15:30:00+09:00")) # round-trip
시간대 없는 값과 있는 값 구분하기·python
from datetime import datetime, timezone
from zoneinfo import ZoneInfo
naive = datetime(2026, 5, 2, 15, 30)
aware = datetime(2026, 5, 2, 15, 30, tzinfo=timezone.utc)
# 산술에서 섞으면 raise
try:
aware - naive
except TypeError as e:
print("실패:", e)
# naive 를 aware 로 변환 (UTC 가정)
aware_from_naive = naive.replace(tzinfo=timezone.utc)
print(aware - aware_from_naive) # 0 — 같은 순간
# aware 를 다른 zone 으로
seoul = aware.astimezone(ZoneInfo("Asia/Seoul"))
print(seoul) # 2026-05-03 00:30:00+09:00
timedelta로 날짜 계산하기·python
from datetime import datetime, timedelta, timezone
now = datetime.now(timezone.utc)
in_a_week = now + timedelta(days=7)
yesterday = now - timedelta(days=1)
print(in_a_week - now) # 7 days, 0:00:00
print(now - yesterday) # 1 day, 0:00:00
# 총 초
delta = in_a_week - now
print(delta.total_seconds()) # 604800
# 컴포넌트
print(delta.days) # 7
print(timedelta(hours=25).days) # 1 — 시간이 일로 overflow
ISO가 아닌 형식을 strftime과 strptime으로 다루기·python
from datetime import datetime
dt = datetime(2026, 5, 2, 15, 30)
# strftime — datetime to 문자열
print(dt.strftime("%Y-%m-%d")) # 2026-05-02
print(dt.strftime("%B %d, %Y")) # May 02, 2026
print(dt.strftime("%I:%M %p")) # 03:30 PM
# strptime — 문자열 to datetime
parsed = datetime.strptime("05/02/2026 15:30", "%m/%d/%Y %H:%M")
print(parsed)
# 가능하면 fromisoformat 선호. 못 바꿀 non-ISO 포맷에만 strptime.
날짜 차이와 요일 구하기·python
from datetime import date, timedelta
birthday = date(2025, 6, 15)
today = date.today()
diff = (today - birthday).days
print(f"생일부터 {diff} 일")
# 요일 — 0=월요일, 6=일요일
print(today.weekday()) # int
print(["월", "화", "수", "목", "금", "토", "일"][today.weekday()])
# strftime 으로 요일 이름
print(today.strftime("%A")) # 'Saturday' (또는 뭐든)
# 다음 월요일 찾기
days_until_monday = (7 - today.weekday()) % 7 or 7
print(today + timedelta(days=days_until_monday))