严格别名和std :: array vs C风格的数组

时间:2012-05-12 11:45:10

标签: c++ arrays reinterpret-cast strict-aliasing type-punning

使用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

为什么他们的待遇不同?

1 个答案:

答案 0 :(得分:3)

当获取std::array的地址时,表达式arr[0]等同于函数调用arr.operator[](0),它返回引用,而不是指针算术表达式(arr + 0)。在生成别名警告时,编译器可能不会尝试“查看”operator[]函数调用。