为什么我不能将 chrono::weekday 与 operator<() 进行比较?

How*_*ant 5 c++ c++-chrono c++20

在新的 C++20<chrono>头文件中有一个std::chrono::weekday类型。为什么我不能将weekdays 与operator<它们进行比较并对它们进行排序?

auto wd1 = Wednesday;
auto wd2 = Thursday;
if (wd1 < wd2)  // compile-time error
{
    // do something
}

test.cpp:14:13: error: invalid operands to binary expression (std::chrono::weekday and 
std::chrono::weekday)
if (wd1 < wd2)
    ~~~ ^ ~~~
Run Code Online (Sandbox Code Playgroud)

星期三不是比星期四少吗?

How*_*ant 12

在此看来<chrono>,没有Wednesday不小于Thursday

Thursday - Wednesday确实等于days{1}. 然而Wednesday - Thursday等于days{6},不是days{-1}

在现代文化中,关于哪一天是一周的第一天存在分歧。该<chrono>库负责认为,我们没有同意在哪一天是一周的第一天。我们可以在没有这种协议的情况下对一周中的几天进行有意义的计算。

为了便于此类计算,<chrono>将工作日视为一个独立的日历,每 7 天重复一次,7 天周期中的任何一个都绝对没有区别。周一在周日之后,周四在周三之后,周日在周六之后。它是一个包含七个值的圆形范围,没有开始也没有结束。

实际上,就整数值而言,工作日有两种流行的编码:

  1. C 将 [星期日,星期六] 编码为 [0, 6]。
  2. ISO 将 [Monday, Sunday] 编码为 [1, 7]。

<chrono>通过在weekday构造函数中接受 [0, 7]来分别表示Sunday, Monday, Tuesday, Wednesday, Thursday, Friday, Saturday,来确认这一点Sunday。并启用反向转换weekday有两个成员函数:

  1. c_encoding()
  2. iso_encoding()

weekday根据这两个协议返回与存储关联的整数值(星期日为 0 或 7,星期一到星期六为 1 到 6)。

然而,std::chrono::weekday对于涉及 的计算, 的底层编码应该被视为一个不重要的细节weekday

std::chrono::weekday是 7 个值的圆形范围。没有任何值大于任何其他值。它们要么相等,要么不相等。

任何两个weekday值(比如xy)之间的差异导致 的数量days x领先于y。这是真的,无论您想象的数字编码weekday在引擎盖下代表什么。

这意味着Wednesday不小于Thursday. Wednesday是提前6天Thursday,和Thursday领先的第1天Wednesday

这种设计可以在不依赖于底层编码的情况下进行诸如“从这个日期开始的下一个星期一是什么”之类的计算:

std::chrono::sys_days
next_monday(std::chrono::sys_days x)
{
    using namespace std::chrono;
    return x + (Monday - weekday{x});
}
Run Code Online (Sandbox Code Playgroud)

用英语:

x的工作日比星期一晚多少天?将那么多天添加到x.

  • 至少,“星期一”显然应该少于“星期五”。我们可以破例吗:-) (2认同)