c++ - Consexpr if 具有非 bool 条件

标签 c++ language-lawyer c++17 implicit-conversion compiler-bug

我似乎发现了 Clang 和 GCC 不同意的地方。代码如下:

int main() {
  if constexpr (2) {}
}

使用 GCC 7.4.0 编译成功,但使用 Clang 7.0.0 编译失败,并显示以下错误消息:

test.cpp:3:17: error: constexpr if condition evaluates to 2, which cannot be narrowed to type 'bool'
      [-Wc++11-narrowing]
  if constexpr (2) {}
                ^
1 error generated.

cppreference似乎没有提到“缩小”,所以这似乎是一个 Clang 错误,但我并不完全确定。如果这是任一编译器的错误,是否已报告?

最佳答案

Clang 正在根据这些段落进行诊断

[stmt.if] (emphasis mine)

2 If the if statement is of the form if constexpr, the value of the condition shall be a contextually converted constant expression of type bool; this form is called a constexpr if statement.

[expr.const]

4 A converted constant expression of type T is an expression, implicitly converted to type T, where the converted expression is a constant expression and the implicit conversion sequence contains only

  • integral conversions other than narrowing conversions,

现在,当涉及到整数转换时,to bool is listed as an integral conversion .从最严格的意义上讲,它正在缩小,因为 bool 不能代表 int 的所有值。所以诊断并非没有根据。

但我认为考虑到 bool 的转换通常是为了检查“真实性”这一事实也是相当合理的,因此它的缩小性质应该无关紧要。它看起来像是标准1 中的一个小错误,GCC 走的是常识路线,而 Clang 遵守最严格意义上的法律条文。


<子> 1 - 和 a proposal exists to change it .

关于c++ - Consexpr if 具有非 bool 条件,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/54899466/

相关文章:

c++ - 为什么互斥锁和条件变量可以轻松复制?

c++ - std::span 默认构造函数的当前标准规范在 "Extent <= 0"上是否正确?

c++ - 这是缓存线程安全(c++)的通用实现吗?

c++ - Visual Studio 2017 - 无法推断模板参数(使用可变参数模板)

c++ - 调用堆栈和堆栈有什么区别?

c++ - 如何使用 C++ 写入、编辑和检索 Excel 文档中的特定单元格?

c++ - 从通用 lambda 调用 `this` 成员函数 - clang vs gcc

c++ - 从 C++ 中的类型列表获取类型索引

c++ - 旋转其中一个物体后,如何将两个物体移动到同一方向?

c++ - 我需要有人向我解释这些代码行