限制指针和内联
Restrict pointers and inlining
本文关键字:指针 更新时间:2023-10-16
我曾尝试使用限制限定指针,但遇到了一个问题。下面的程序只是一个简单的程序,只是为了说明问题。
calc_function使用三个指针,这是受限制的,因此它们"SHALL"不会彼此别名。在visual studio中编译此代码时,函数将被内联,因此visual studio 2010会毫无理由地忽略限定符。如果我禁用内联,代码的执行速度会快六倍多(从2200ms到360ms)。但我不想在整个项目或整个文件中禁用内联(因为这将是所有getter和setter的调用开销,这将是可怕的)。
(唯一的解决方案可能是只禁用这个函数的内联吗?)
我试图在函数中创建临时的限制限定指针,包括在顶部和内部循环中,试图告诉编译器我保证没有别名,但编译器不会相信我,它也不会工作。我也尝试过调整编译器设置,但我发现唯一有效的方法是禁用内联。
我希望能为解决这个优化问题提供一些帮助。
要运行程序(在realeasemode中),不要忘记使用参数0 1000 2000。为什么使用用户输入/程序参数是为了确保编译器不知道指针a、b和c之间是否存在混叠。
#include <cstdlib>
#include <cstdio>
#include <ctime>
// Data-table where a,b,c will point into, so the compiler cant know if they alias.
const size_t listSize = 10000;
int data[listSize];
//void calc_function(int * a, int * b, int * c){
void calc_function(int *__restrict a, int *__restrict b, int *__restrict c){
for(size_t y=0; y<1000*1000; ++y){ // <- Extra loop to be able to messure the time.
for(size_t i=0; i<1000; ++i){
*a += *b;
*c += *a;
}
}
}
int main(int argc, char *argv[]){ // argv SHALL be "0 1000 2000" (with no quotes)
// init
for(size_t i=0; i<listSize; ++i)
data[i] = i;
// get a, b and c from argv(0,1000,2000)
int *a,*b,*c;
sscanf(argv[1],"%d",&a);
sscanf(argv[2],"%d",&b);
sscanf(argv[3],"%d",&c);
a = data + int(a); // a, b and c will (after the specified argv) be,
b = data + int(b); // a = &data[0], b = &data[1000], c = &data[2000],
c = data + int(c); // So they will not alias, and the compiler cant know.
// calculate and take time
time_t start = clock();
funcResticted(a,b,c);
time_t end = clock();
time_t t = (end-start);
printf("funcResticted %u (microSec)n", t);
system("PAUSE");
return EXIT_SUCCESS;
}
如果用__declspec(noinline)
声明函数,它将强制它不内联:
http://msdn.microsoft.com/en-us/library/kxybs02x%28v=vs.80%29.aspx
您可以使用它在每个函数的基础上手动禁用内联。
至于restrict
,编译器只有在需要时才可以自由使用。因此,在试图"欺骗"编译器进行此类优化时,篡改同一代码的不同版本是不可避免的。
相关文章:
- 1d 智能指针不适用于语法 (*)++
- 在C#中处理C++指针而不使用unsafe的最佳方法
- 为什么使用 "this" 指针调用派生成员函数?
- 函数向量_指针有不同的原型,我可以构建一个吗
- 使用指针从C++中的数组中获取最大值
- 助记符和指向成员语法的指针
- 嵌入方指针压缩已禁用
- 数组的指针从不分段故障
- C++ 指针的内存地址和指向数组的内存地址如何相同?
- 何时在引用或唯一指针上使用移动语义
- QMetaObject invokeMethod的基于函数指针的语法
- 如何从 std::atomic 中提取指针 T<T>?
- 如何在 C# 中映射双 C 结构指针?
- C++将浮点指针值舍入为小数位数
- 为什么++(*p)更改指针值
- 调整大小后指向元素值的指针unordered_map有效?
- 正在将指针转换为范围
- 使用指向成员的指针将成员函数作为参数传递
- 将OpenCV C++重写为EmguCV C#-如何使用指针
- C++-试图将函数指针推回到另一个CPP文件中的矢量时出错