6

指数とそれに続く乗算を使用して単純な式を評価すると、ポートランドとインテルのFortranコンパイラーで異なる動作が発生します。演算子の優先順位の理解に基づいて、pgf90(およびgfortran)が正しく機能していることはかなり確信していますが、これらは少し注意が必要な場合があるため、セカンドオピニオンをお願いします。

これが私のコードを非常に基本的な形に簡略化したものです。ifortを使用して実行すると、フォームの式は、pgf90およびgfortranによってifortによってd1=a**-2*b解釈されます。指数から負の符号を削除すると、3つのコンパイラすべてがこれを。として解釈します。*bを+bに変更すると、3つすべてからも良好な動作が得られます。d1=a**(-2*b)d1=(a**-2)*bd1=(a**2)*b

program badvals
  implicit none
  real :: a, b, c1, c2, d1, d2

  a = 2.
  b = 4.

  ! Works with addition following the exponent.
  c1 = a**-2+b
  c2 = a**(-2)+b

  ! Ifort differs with multiplication following negative exponent.
  d1 = a**-2*b
  d2 = a**(-2)*b

  print*, "c1, d1       = ",c1, d1
  print*, "c2, d2       = ",c1, d2
  print*, "c2-c1, d2-d1 = ",c2-c1, d2-d1
end program badvals

!Program output for ifort v13.0.1.117: (either -O0 or -fast):
! c1, d1       =    4.250000      3.9062500E-03
! c2, d2       =    4.250000       1.000000
! c2-c1, d2-d1 =   0.0000000E+00  0.9960938

!Program output for pgf90 v12.10-0: (either -O0 or -fast):
! c1, d1       =     4.250000        1.000000
! c2, d2       =     4.250000        1.000000
! c2-c1, d2-d1 =     0.000000        0.000000

!Program output for gfortran v4.1.2: (either -O0 or -O3):
! c1, d1       =    4.250000       1.000000
! c2, d2       =    4.250000       1.000000
! c2-c1, d2-d1 =    0.000000       0.000000

これらの違いの背後にある歴史があり、それらは「機能」と見なされるべきですか?それとも、これはIntel側の完全なバグですか?

4

1 に答える 1

6

Webを検索すると、2つの連続する演算子は許可されていないというステートメントが見つかりました。したがって、この表現を拒否するのではなく解釈することは、言語の拡張です。この拡張機能は、コンパイラベンダーによって実装が異なります。

実際、制限付きのコンパイラオプションを指定してgfortranを使用すると、次のコード例が拒否されます。

badvals.f90:9.11:
  c1 = a**-2+b
           1
Error: Extension: Unary operator following arithmetic operator (use parentheses) at (1)
badvals.f90:13.11:

  d1 = a**-2*b
           1
Error: Extension: Unary operator following arithmetic operator (use parentheses) at (1)

同様に、制限付きコンパイラオプションを使用したifortは、次のことを提供します。

badvals.f90(9): warning #7026: Non-standard extension
  c1 = a**-2+b
----------^
badvals.f90(13): warning #7026: Non-standard extension
  d1 = a**-2*b
----------^

したがって、1)コンパイラの警告およびエラーオプションを使用すると非常に役立ちます。2)バグよりも拡張機能です。3)この式が言語で許可されている場合でも、gfortranのアドバイスは適切です。必要がない場合でも明確さ。

于 2013-03-14T18:20:08.630 に答える