gpt4 book ai didi

c - 对于繁重的计算,Fortran 是否比 C 更容易优化?

转载 作者:太空狗 更新时间:2023-10-29 16:13:33 24 4
gpt4 key购买 nike

我时常读到 Fortran 在繁重的计算方面比 C 快或可能比 C 快。真的是这样吗?我必须承认我几乎不了解 Fortran,但到目前为止我看到的 Fortran 代码并没有表明该语言具有 C 所没有的特性。

如果是真的,请告诉我为什么。请不要告诉我哪些语言或库适用于数字运算,我不打算编写应用程序或库来执行此操作,我只是好奇。

最佳答案

这些语言具有相似的功能集。性能差异来自 Fortran 表示不允许使用别名这一事实,除非使用 EQUIVALENCE 语句。任何有别名的代码都不是有效的 Fortran,但检测这些错误的责任在于程序员而不是编译器。因此 Fortran 编译器忽略了可能的内存指针别名,并允许它们生成更高效的代码。看一下 C 中的这个小例子:

void transform (float *output, float const * input, float const * matrix, int *n)
{
int i;
for (i=0; i<*n; i++)
{
float x = input[i*2+0];
float y = input[i*2+1];
output[i*2+0] = matrix[0] * x + matrix[1] * y;
output[i*2+1] = matrix[2] * x + matrix[3] * y;
}
}

此函数在优化后会比 Fortran 函数运行得更慢。为什么这样?如果将值写入输出数组,则可能会更改矩阵的值。毕竟,指针可以重叠并指向同一 block 内存(包括 int 指针!)。 C 编译器被迫从内存中重新加载四个矩阵值以进行所有计算。

在 Fortran 中,编译器可以一次加载矩阵值并将它们存储在寄存器中。它可以这样做,因为 Fortran 编译器假定指针/数组在内存中不重叠。

幸运的是,restrict关键字和严格别名已被引入 C99 标准以解决此问题。现在大多数 C++ 编译器也很好地支持它。该关键字允许您向编译器提供一个提示,即程序员 promise 某个指针不会与任何其他指针互为别名。严格别名意味着程序员 promise 不同类型的指针永远不会重叠,例如 double* 不会与 int* 重叠(特定的异常(exception)是char*void* 可以与任何内容重叠)。

如果您使用它们,您将获得与 C 和 Fortran 相同的速度。但是,仅对性能关键函数使用 restrict 关键字的能力意味着 C(和 C++)程序更安全且更易于编写。例如,考虑无效的 Fortran 代码:CALL TRANSFORM(A(1, 30), A(2, 31), A(3, 32), 30),大多数 Fortran 编译器都乐于对其进行编译没有任何警告,但引入了一个错误,该错误仅出现在某些编译器、某些硬件和某些优化选项上。

关于c - 对于繁重的计算,Fortran 是否比 C 更容易优化?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/146159/

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