datetime의 날짜가 몇 번째 주에 속하는지 출력하려고 합니다. 이 때 잘못 적용하면 의도치 않는 결과가 나타날 수 있습니다. 특히, 1월 새해 근처에 있는 코너 케이스로 테스트를 해 보셔야 어떤 주에 속하는지 정확하게 알 수 있습니다.

 


 먼저 2020년 12월 25일부터 14일 동안 년도와 몇 번째 주차인지 뽑는 프로그램을 만들어 보겠습니다. strftime으로 datetime을 문자열로 변환하는데요. 변환 문자열이 '%Y-%W'임을 알 수 있습니다. 년도와 주차가 뽑히게 되는데요. iso 8601 형식이 아닙니다. 어떻게 뽑히는지 보겠습니다.

 

 2020년 12월 28일이 2020년 52번째 주차로 뽑힙니다. 그리고 2021년 1월 1일이 2021년 0번째 주차, 1월 4일이 1번째 주차로 뽑히게 되는데요. 2020년 12월 근처의 달력을 보겠습니다.

 

 2020년 12월 28일은 월요일입니다. 그래서 주차가 바뀝니다. 다음에 2021년 1월 1일에 주차가 또 바뀌었음을 알 수 있는데요. 이는 2020년에서 2021년으로 바뀌었기 때문입니다. 다음에 2021년 1월 4일은 월요일입니다. 따라서, 2021년 1월 4일은 주차가 또 바뀝니다.

 

 즉, strftime에서 %Y-%W를 입력하면, 연도가 바뀔 때와 월요일이 되었을 때 주차가 바뀌게 됩니다. 그렇기 때문에 1월 1일이 월요일이 아닌 경우 의도치 않은 결과가 나올 수 있습니다.

 


 이를 해결하기 위해서는 Week와 Year를 ISO year, week로 바꾸어야 합니다. ISO year는 %G, ISO week는 %V입니다. 이는 문서를 보면 알 수 있습니다.

 

 다시 2020년 12월 25일부터 14일동안 iso 형식의 year와 week를 뽑아보겠습니다.

 

 그러면 아까와는 다르게, 2021년 1월 4일, 2020년 12월 28일에 주차가 바뀜을 알 수 있습니다. week가 시작하는 월요일을 기준으로 주의 번호가 변하게 됩니다. 2020-53이 1월 1일이 되었다고 바뀌지 않는 것을 보면 알 수 있습니다.

 

2022년에서 2023년으로 변하는 데이터의 경우에도 제대로 작동할까요?

 

 2022년 12월 26일에 월요일이 되었습니다. 그리고, 2023년 1월 2일에 월요일이 됩니다. 따라서, 주차를 정확하게 구했다면, 2022년 12월 26일의 week와 2023년 1월 1일의 week가 같아야 합니다. 정말 그런지 보겠습니다.

 

 2022-52로 같음을 알 수 있습니다.

 

 

 isocalendar를 써도 동일한 결과를 얻을 수 있습니다. 이것은 iso year, week, day를 튜플 형태로 리턴하게 되는데요. 맨 먼저 나오는 것이 year, 두 번째로 나오는 것이 week, 마지막으로 나오는 것이 day입니다.

 

 사용법은 어렵지 않습니다. datetime의 datetime 객체 dt가 있다면, dt.isocalendar()를 호출해 주면 iso year, week, day가 있는 튜플이 나오게 됩니다. 이 정보를 그대로 쓰면 됩니다. 프로그램의 실행 결과는 아래와 같습니다.

 

 2022년 12월 31일과 2023년 1월 1일이 같은 주차로 묶였음을 알 수 있습니다.