在 C++ Core Guidelines Per.4 中,为什么坏示例旨在更快?

rus*_*yhu 5 c++ performance cpp-core-guidelines

我最近正在阅读这篇文章,其中指出:

不要认为复杂的代码一定比简单的代码快。

代码复制如下:

例子,不错

// clear expression of intent, fast execution

vector<uint8_t> v(100000);

for (auto& c : v)
    c = ~c;
Run Code Online (Sandbox Code Playgroud)

例子,坏

// intended to be faster, but is often slower

vector<uint8_t> v(100000);

for (size_t i = 0; i < v.size(); i += sizeof(uint64_t)) {
    uint64_t& quad_word = *reinterpret_cast<uint64_t*>(&v[i]);
    quad_word = ~quad_word;
}
Run Code Online (Sandbox Code Playgroud)

我不确定坏例子的目的是什么,为什么它打算更快
为什么它实际上通常更慢

Nic*_*las 5

通过将指针转换为 64 位整数并对该整数执行按位运算,您可以将 C++ 代码执行的运算次数减少 8 倍。也就是说,所做出的假设是性能受用 C++ 代码编写的操作数。

  • 坏处是(我猜)编译器可以轻松地向量化字节循环,但可能会遇到 `reinterpret_cast` 问题,特别是如果 `v` 不是 8 字节对齐的 (3认同)

Ale*_*iev 3

编译器会尝试使用 SIMD 指令(x86-64 上的 SSE/AVX,其他平台上的其他指令)同时执行多个操作来向量化操作。

通过手动矢量化,uint64_t您可以使编译器一次执行 8 个操作,您认为这是调试构建的改进,但可能会阻止它一次执行更多操作(例如,使用 SSE2 执行 16 个操作,使用 AVX2 执行 32 个操作,使用 AVX512 执行 64 个操作) ,您认为发布速度较慢。