[英]undefined reference to class static constexpr struct, g++ vs clang
[英]G++ vs Clang : inconsistent behavior for constexpr and const
考虑以下代码:
constexpr const int A = 42;
const int &B = A;
static_assert(&A == &B, "Bug");
constexpr const int &C = B;
static_assert(&A == &C, "Bug");
int main() { return 0; }
它被clang版本3.3完全接受,而g ++(SUSE Linux)4.8.1 20130909 [gcc-4_8-branch版本202388拒绝使用以下命令:
bug2.cpp:5:1: error: non-constant condition for static assertion
static_assert(&A == &B, "Bug");
^
bug2.cpp:5:1: error: the value of ‘B’ is not usable in a constant expression
bug2.cpp:2:12: note: ‘B’ was not declared ‘constexpr’
const int &B = A;
^
在我看来,GCC是正确的(而我当然更喜欢clang行为)。 尝试阅读标准时,我意识到我还没有足够的语言律师来决定。 谁能确认?
the value of 'B' is not usable in a constant expression
是不正确的。 您没有在B上执行从左值到右值的转换,这是“值”的通常含义。 您仅使用其地址。 唯一相关的常量表达式规则禁止:
引用引用类型的变量或数据成员的id表达式,除非引用具有先前的初始化,且使用常量表达式初始化;
但是, B
确实对参考常量表达式进行了初始化。
引用常量表达式是左值核心常量表达式,用于指定具有静态存储持续时间或函数的对象。
在这种情况下, B
的初始值设定项是A
,它的常数要尽可能大。 A
和B
静态引用相同的对象。
因此,这是一个GCC错误。
如果您不是语言律师,则通常不能将引用用作常量表达式,只能使用值(如果有例外,请纠正我)。 从这个意义上讲,最接近您的代码的有效值为:
constexpr int A = 42;
constexpr int B = A;
static_assert(A == B, "Bug");
但是,就我而言,Clang 3.3和GCC 4.8.1都会在您的代码上出现预期的错误。
编辑显然,我的知识仍然有点狭窄,对不起。 根据链接的不同,可能会有一些例外情况,例如,如果语句是全局的,则在main()
之外接受( 实时 )代码。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.