使用gcc 4.7(在OS X上使用MacPorts构建的g ++ - mp-4.7(GCC)4.7.0)编译以下代码时,我看到了看似矛盾的结果。
当我尝试将std::array
的一部分重新解释和取消引用为uint32_t
时,编译器不会抱怨,但是当使用C风格的数组时它会这样做。
示例代码:
#include <array>
#include <cstdint>
int main() {
std::array<uint8_t, 6> stdarr;
*reinterpret_cast<uint32_t*>(&stdarr[0]) = 0; // OK
uint8_t arr[6];
*reinterpret_cast<uint32_t*>(&arr[0]) = 0;
// ^ error: dereferencing type-punned pointer will break strict-aliasing rules [-Werror=strict-aliasing]
}
编译器命令是:
$ g++ -o test -std=c++0x -Wall -Wextra -Werror main.cpp
为什么他们的待遇不同?
答案 0 :(得分:3)
当获取std::array
的地址时,表达式arr[0]
等同于函数调用arr.operator[](0)
,它返回引用,而不是指针算术表达式(arr + 0)
。在生成别名警告时,编译器可能不会尝试“查看”operator[]
函数调用。