std::is_trivially_equality_comparable_v<T>

Quu*_*one 6 c++ type-traits language-lawyer c++20

相关但比C++11 相等可比较类型的静态断言更神秘?\xe2\x80\x94

\n\n

JF Bastien 的论文N4130“Pad Thy Atomics!” 让我想到如果我们要使用atomic<T>::compare_exchange_weak()whereT是类或结构类型,例如

\n\n
struct Count {\n    int strong_count;\n    int weak_count;\n};\n
Run Code Online (Sandbox Code Playgroud)\n\n

那么我们真的想静态断言两件事:

\n\n

首先,这T实际上是无锁原子的:

\n\n
template<class T>\nstatic constexpr bool is_lockfree_atomic_v =\n    std::atomic<T>::is_always_lock_free;\n
Run Code Online (Sandbox Code Playgroud)\n\n

其次,这compare_exchange_weak将实现我们想要的。回想一下(或来自 N4130)compare_exchange_weak是根据memcmp和定义的memcpy。因此,我们需要检查这些函数是否会做正确的事情T

\n\n
template<class T>\nstatic constexpr bool is_cmpxchgable_v =\n    std::is_trivially_copyable_v<T> &&\n    is_trivially_equality_comparable_v<T>;\n
Run Code Online (Sandbox Code Playgroud)\n\n

is_trivially_copyable_v由STL提供。但我们还没有is_trivially_equality_comparable_v\xe2\x80\x94 ,遗憾的是,我的理解是P0515 一致比较不建议提供一个。(P0515 是允许编译器检测等于运算符实际上是“琐碎的”\xe2\x80\x94 的功能,它不是用户提供的,并且在这样那样的条件下显式默认。但是,它没有在核心语言中引入任何新概念,例如“平凡可比”。)

\n\n

我对“基本可比”特征的最佳尝试如下:

\n\n
template<class T, class U>\nstatic constexpr bool is_equality_comparable_with_v =\n    requires(std::declval<T>() == std::declval<U>());\n\ntemplate<class T>\nstatic constexpr bool is_equality_comparable_v =\n    is_equality_comparable_with_v<T, U>;\n\ntemplate<class T>\nstatic constexpr bool is_trivially_equality_comparable_v =\n    is_equality_comparable_v<T> &&\n    std::has_unique_object_representations_v<T>;\n
Run Code Online (Sandbox Code Playgroud)\n\n

但是,此定义依赖于std:: has_unique_object_representations_v,[编辑:当不是标量类型时,它具有未定义的行为operator==,其值与]的行为无关。T我强烈怀疑在实践中 has_unique_object_representations_v会为结构类型(例如我的原始Count类型)返回垃圾。

\n\n
struct Yes { int a; int b; };\nstruct No { short a; int b; };\nusing Yes2 = std::tuple<int, int>;\nstruct No2 { int a; int b; bool operator==(const No2&) { return true; }};\n
Run Code Online (Sandbox Code Playgroud)\n\n
    \n
  • Clang/libc++ 尚未实现has_unique_object_representations
  • \n
  • 据我所知, MSVC 尚未实施has_unique_object_representations
  • \n
  • GCC/libstdc++ 说has_unique_object_representations_v<Yes>甚至正确地报告了那个not has_unique_object_representations_v<No>,但错误地报告了那个not has_unique_object_representations_v<Yes2>和那个has_unique_object_representations_v<No2>
  • \n
\n\n
\n\n

所以我的问题是,(1)有没有更好的方法来测试“微不足道的可比性”?is_trivially_equality_comparable(2) 如果 P0515 进入C is_trivially_less_than_comparable++20 标准,在提案方向上是否有任何进展?(3) 应该有吗?

\n

JF *_*ien 5

我想你想要has_padding_bits。p0528 详细解释了原因。简而言之,您说得完全memcpy正确memcmp

杰克逊维尔会议前将有一份更新的文件。

2018 年中更新

标准委员会决定采用 p0528 走向另一个方向,转而使用带有填充位的类型来制作 cmpxchg Just Work。has_padding_bitsp0528 想要解决的问题不会有。

目前没有很好的答案来回答您的问题:-)