如何使用C++20 <chrono>自行计算ISO周基日期相关值
用C++ 库计算ISO周历值(%G、%V、%u)
ISO周历的核心规则:
- 每周从周一开始(%u的取值为1=周一,7=周日)
- 一年的第1周(%V=01)是包含当年第一个周四的周,因此ISO年(%G)可能与格里高利年不一致(比如2023年12月31日属于2024年的第1周)
下面是基于C++20
1. 计算ISO星期几(%u)
利用weekday类型获取日期对应的星期,再调整为ISO规则(周一=1,周日=7):
#include <chrono> #include <iostream> using namespace std::chrono; unsigned get_iso_weekday(const sys_days& date) { weekday wd{date}; // chrono中weekday的unsigned值为0=周日,1=周一,...,6=周六 return wd == weekday{0} ? 7 : static_cast<unsigned>(wd); }
2. 计算ISO年(%G)
ISO年由日期所在周的周四对应的格里高利年决定(因为ISO周归属以周四所在年份为准):
year get_iso_year(const sys_days& date) { weekday wd{date}; // 找到当前日期所在周的周四 sys_days thurs = date + (weekday{4} - wd); // 提取周四所在的年份即为ISO年 return year{floor<years>(thurs)}; }
3. 计算ISO周数(%V)
先找到ISO年的第一个周四,推导该年第1周的周一,再计算目标日期所在周与第1周的间隔:
unsigned get_iso_week(const sys_days& date) { weekday wd{date}; // 目标日期所在周的周一 sys_days target_monday = date - (wd - weekday{1}); year iso_y = get_iso_year(date); // 找到ISO年1月1日的星期 weekday jan1_wd{sys_days{iso_y/1/1}}; // ISO年的第一个周四 sys_days first_thurs = sys_days{iso_y/1/1} + (weekday{4} - jan1_wd); // ISO年第1周的周一(周四往前推3天) sys_days first_week_monday = first_thurs - days{3}; // 计算两个周一之间的天数差,除以7得到周数,加1是因为从第1周开始计数 return (target_monday - first_week_monday) / days{7} + 1; }
测试示例
int main() { // 测试2023年12月31日(属于2024年第1周,周日) auto date1 = sys_days{2023y/12/31}; std::cout << "日期: " << year_month_day{date1} << "\n"; std::cout << "ISO年(%G): " << get_iso_year(date1) << "\n"; std::cout << "ISO周数(%V): " << get_iso_week(date1) << "\n"; std::cout << "ISO星期几(%u): " << get_iso_weekday(date1) << "\n\n"; // 测试2024年1月1日(属于2024年第1周,周一) auto date2 = sys_days{2024y/1/1}; std::cout << "日期: " << year_month_day{date2} << "\n"; std::cout << "ISO年(%G): " << get_iso_year(date2) << "\n"; std::cout << "ISO周数(%V): " << get_iso_week(date2) << "\n"; std::cout << "ISO星期几(%u): " << get_iso_weekday(date2) << "\n"; return 0; }
输出结果:
日期: 2023-12-31 ISO年(%G): 2024 ISO周数(%V): 1 ISO星期几(%u): 7 日期: 2024-01-01 ISO年(%G): 2024 ISO周数(%V): 1 ISO星期几(%u): 1
内容的提问来源于stack exchange,提问作者Howard Hinnant
相关产品推荐
相关产品推荐

