我尝试使用forall来分配动态数组,但是gfortran不喜欢这样。我还发现write语句在forall块中是被禁止的,我怀疑read语句也是如此。
forall块中不允许使用哪些其他函数/操作?
除了有时在顺序无关紧要的时候替换do循环之外,这个构造到底是为了什么?我认为这会使编码更加清晰和优雅,特别是在操作顺序不重要时显示出来,但它似乎对在forall中可以完成的操作有很大的限制。
这些限制的原因是什么,即它们保护/防止用户搞砸的是什么?使用forall是个好主意吗?如果是这样的话,目的是什么?
现在,在我正在处理的代码中,只有一个forall块,如果我把它全部翻译成do循环,它会给出四个嵌套循环。哪种方式更好?
发布于 2011-12-22 23:57:06
现在对FORALL和WHERE构造的需求不大。它们是作为Fortran 95 (对Fortran 90的次要扩展)的一部分引入的,主要是为了优化的目的,当时代码矢量化是HPC中的主要内容。FORALL在应用上如此有限的原因正是因为它是为循环优化而设计的。还要注意,FORALL不是循环构造,而是赋值。因此,只允许在块内使用赋值语句。从理论上讲,DO循环给出了关于处理器将要循环的索引顺序的明确指令。FORALL结构允许编译器根据数组在内存中的存储方式选择最优的顺序。然而,随着时间的推移,这已经失去了意义,因为现代编译器非常擅长DO循环向量化,而使用FORALL不太可能注意到任何改进。
查看有关FORALL和WHERE here的精彩讨论
如果您担心代码性能,您可能更愿意考虑不同的编译器- PGI或ifort。根据我自己的经验,gfortran适用于开发,但不是真正适用于HPC。您将注意到,使用pgf90或ifort编译的代码执行速度提高了好几倍。
发布于 2011-12-22 19:01:09
事实证明,Forall构造真的限制太多,并且主要用于数组操作。有关确切的限制,请参阅IBM Fortran - FORALL。限制较少的是Fortran2008的do concurrent构造。甚至允许使用read和write语句。参见Intel Fortran - DO CONCURRENT和New features of Fortran 2008。
https://stackoverflow.com/questions/8602596
复制相似问题