gpt4 book ai didi

c++ - 全局变量减慢代码

转载 作者:可可西里 更新时间:2023-11-01 15:37:21 25 4
gpt4 key购买 nike

我正在写我能写的最糟糕的代码,(基本上是想破坏东西)我注意到这段代码:

for(int i = 0; i < N; ++i)
tan(tan(tan(tan(tan(tan(tan(tan(x++))))))));
end
std::cout << x;

其中 N 是一个全局变量,运行速度明显较慢:

int N = 10000;
for(int i = 0; i < N; ++i)
tan(tan(tan(tan(tan(tan(tan(tan(x++))))))));
end
std::cout << x;

全局变量会导致运行速度变慢怎么办?

最佳答案

tl;dr:本地版本将 N 保存在寄存器中,全局版本则不会。使用 const 声明常量,无论您如何声明它都会更快。


这是我使用的示例代码:

#include <iostream>
#include <math.h>
void first(){
int x=1;
int N = 10000;
for(int i = 0; i < N; ++i)
tan(tan(tan(tan(tan(tan(tan(tan(x++))))))));
std::cout << x;
}
int N=10000;
void second(){
int x=1;
for(int i = 0; i < N; ++i)
tan(tan(tan(tan(tan(tan(tan(tan(x++))))))));
std::cout << x;
}
int main(){
first();
second();
}

(名为 test.cpp)。

为了查看生成的汇编代码,我运行了 g++ -S test.cpp

我得到了一个很大的文件,但通过一些智能搜索(我搜索了 tan),我找到了我想要的:

来自 first 函数:

Ltmp2:
movl $1, -4(%rbp)
movl $10000, -8(%rbp) ; N is here !!!
movl $0, -12(%rbp) ;initial value of i is here
jmp LBB1_2 ;goto the 'for' code logic
LBB1_1: ;the loop is this segment
movl -4(%rbp), %eax
cvtsi2sd %eax, %xmm0
movl -4(%rbp), %eax
addl $1, %eax
movl %eax, -4(%rbp)
callq _tan
callq _tan
callq _tan
callq _tan
callq _tan
callq _tan
callq _tan
movl -12(%rbp), %eax
addl $1, %eax
movl %eax, -12(%rbp)
LBB1_2:
movl -12(%rbp), %eax ;value of n kept in register
movl -8(%rbp), %ecx
cmpl %ecx, %eax ;comparing N and i here
jl LBB1_1 ;if less, then go into loop code
movl -4(%rbp), %eax

第二个功能:

Ltmp13:
movl $1, -4(%rbp) ;i
movl $0, -8(%rbp)
jmp LBB5_2
LBB5_1: ;loop is here
movl -4(%rbp), %eax
cvtsi2sd %eax, %xmm0
movl -4(%rbp), %eax
addl $1, %eax
movl %eax, -4(%rbp)
callq _tan
callq _tan
callq _tan
callq _tan
callq _tan
callq _tan
callq _tan
movl -8(%rbp), %eax
addl $1, %eax
movl %eax, -8(%rbp)
LBB5_2:
movl _N(%rip), %eax ;loading N from globals at every iteration, instead of keeping it in a register
movl -8(%rbp), %ecx

因此从汇编代码中您可以看到(或看不到),在本地版本中,N 在整个计算过程中保存在一个寄存器中,而在全局版本中,N 在每次迭代时从全局重新读取。

我想发生这种情况的主要原因是线程之类的事情,编译器无法确定 N 未被修改。

如果你在 N 的声明中添加一个 const (const int N=10000),它会比本地版本更快:

    movl    -8(%rbp), %eax
addl $1, %eax
movl %eax, -8(%rbp)
LBB5_2:
movl -8(%rbp), %eax
cmpl $9999, %eax ;9999 used instead of 10000 for some reason I do not know
jle LBB5_1

N 被替换为常量。

关于c++ - 全局变量减慢代码,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/15216279/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com