我知道以下应该是未定义的行为,因为最初的变量是const。然而,怎么可能两个地址&x和&rx是相同的,但是它们打印的值(我不是说持有,因为它不能)不是。谢谢!
const int x=10;
int& rx = const_cast<int&>(x);
rx++;
cout << x << " and " << rx << endl;
cout << "is &x == &xr: " << (&x==&rx) << endl;G++ 4.9的输出是
10 and 11
is &x == &xr: 1发布于 2015-01-28 22:50:50
编译器(截至上周的clang++ 3.7.0 )确实优化了代码的“意图”,而不管代码的合法性如何:
movl $_ZSt4cout, %edi
movl $10, %esi
callq _ZNSolsEi
movq %rax, %rbx
movl $.L.str, %esi
movl $5, %edx
movq %rbx, %rdi
callq _ZSt16__ostream_insertIcSt11char_traitsIcEERSt13basic_ostreamIT_T0_ES6_PKS3_l
movl $11, %esi
movq %rbx, %rdi
callq _ZNSolsEi与往常一样,值得注意的是,未定义行为的行为确实包括“做你认为它会做的事情”,以及“不做你认为它会做的事情”,这当然适用于这里。
最初是const的值的const_cast是未定义的行为,此时您已经放弃了编译器对“正常行为”的所有权限。现在发生的是编译器编写人员认为是正确的事情--如果这意味着值实际上被放置在只读内存中,那么您的代码将无法成功地更新该值。但在这种情况下,它只是将x优化为常量10,而rx变为11 --因为您实际上不使用x和rx“做任何其他事情”,按照编译器的标准,这“很好”。
发布于 2015-01-28 22:38:30
这显然是一种不明确的行为,因此,据我所知,问题不应该是为什么会发生,而应该是什么使它发生。
我不知道GCC如何翻译和优化代码,但我最好的猜测是,在cout行中,x在编译时被假定为const值(编译器假定是10)所取代。
看一看生成的汇编代码可能会很有趣!
https://stackoverflow.com/questions/28203635
复制相似问题