c++ - 数组可以重叠(别名),还是 GCC 过于谨慎?
问题描述
对于以下 C++ 代码,GCC 8.3 和 Clang 7.0(都带有 -O2)生成对 memmove 的调用,除非使用 -DRESTRICT 进行编译。使用 -DRESTRICT,生成更快的代码(“rep movsq”或 memcpy)。
我认为检查if (&dest != &src)
足以证明没有混叠。GCC 和 Clang 是否在这里遗漏了一个技巧,或者在 C++ 中即使进行此检查也存在别名是否合法(例如,通过转换更大数组的两个重叠部分来获取 src 和 dest)?
#include <algorithm>
#include <iterator>
typedef int Arr[100];
inline void Copy(Arr& __restrict__ dest, const Arr& __restrict__ src)
{
std::copy(std::begin(src), std::end(src), dest);
}
void f2(Arr& dest, const Arr& src)
{
if (&dest != &src) // make sure there is no aliasing
{
#ifdef RESTRICT
Copy(dest, src); // generates better code, why?
#else
std::copy(std::begin(src), std::end(src), dest);
#endif
}
}