Lat*_*Guy 5 c++ optimization g++ compiler-flags compiler-optimization
当使用下面的基准代码编译时,-O3它在延迟方面的差异给我留下了深刻的印象,所以我开始怀疑编译器是否通过以某种方式删除代码而“作弊”。有没有办法检查?我可以安全地进行基准测试-O3吗?期望速度提高 15 倍是否现实?
没有的结果-O3:平均:239纳米最小:230 纳米(900 万次迭代) 有
结果-O3:平均:14纳米,最小:12 纳米(900 万次迭代)
int iterations = stoi(argv[1]);
int load = stoi(argv[2]);
long long x = 0;
for(int i = 0; i < iterations; i++) {
long start = get_nano_ts(); // START clock
for(int j = 0; j < load; j++) {
if (i % 4 == 0) {
x += (i % 4) * (i % 8);
} else {
x -= (i % 16) * (i % 32);
}
}
long end = get_nano_ts(); // STOP clock
// (omitted for clarity)
}
cout << "My result: " << x << endl;
Run Code Online (Sandbox Code Playgroud)
注意:我clock_gettime用来测量:
long get_nano_ts() {
struct timespec ts;
clock_gettime(CLOCK_MONOTONIC, &ts);
return ts.tv_sec * 1000000000 + ts.tv_nsec;
}
Run Code Online (Sandbox Code Playgroud)
对您认为正在测量的内容进行基准测试可能非常困难。在内循环的情况下:
for (int j = 0; j < load; ++j)
if (i % 4 == 0)
x += (i % 4) * (i % 8);
else x -= (i % 16) * (i % 32);
Run Code Online (Sandbox Code Playgroud)
精明的编译器也许能够看穿这一点并将代码更改为如下所示:
x = load * 174; // example only
Run Code Online (Sandbox Code Playgroud)
我知道这并不等同,但有一些相当简单的表达式可以代替该循环。
确定的方法是使用gcc -S编译器选项并查看它生成的汇编代码。