Sun Studio 12: Fortran プログラミングガイド

7.6.2.4 配列の境界を越えた添字付けによる別名参照

次の例を、-xalias=overindex を使用してコンパイルします。


integer a,z
common // a(100),z
z = 1
call sub(a)
print*, z
subroutine sub(x)
  integer x(10)
  x(101) = 2
コンパイラは、副プログラムの呼び出しが z への書き込みを引き起こす可能性がある
と想定する可能性があります。
-xalias=overindex を使用してコンパイルすると、プログラムは 1 ではなく 2 を
出力します。

配列の境界を越えた添字付けは古い FORTRAN 77 のプログラムの多くに含まれていますが、これらは避けるべきものです。多くの場合は、結果を予測することができません。正しい結果が得られることを確かめるには、プログラムをコンパイルし、-C (境界を越えている添字の検査) オプションを使用してテストします。これによって、配列の添字に問題があるかどうかを調べることができます。

一般に、overindex は古い FORTRAN 77 のプログラムにだけ使用することをお勧めします。-xalias=overindex は、配列、構文式、部分配列、WHERE 文、FORALL 文には適用されません。

正しいコードが生成されるように、Fortran 95 のプログラムを常に Fortran 規格の添字の規則に準拠させるようにしてください。たとえば、次の例では、配列構文式の中で不明確な添字付けが行われているため、常に、配列の境界を越えた添字付けによる誤った結果が得られます。


配列の境界を越えて添字が付けられるこの配列構文の例では、正しい結果が得られません。

   parameter (n=10)
   integer a(n),b(n)
   common /qq/a,b
   integer c(n)
   integer m, k
   a = (/ (i,i=1,n) /)
   b = a
   c(1) = 1
   c(2:n) = (/ (i,i=1,n-1) /)

   m = n
   k = n + n
C
C   a への参照は、実際には b を参照しています。
C  これは本来は b(2:n) = b(1:n-1) であるべきです。
C
   a(m+2:k) = b(1:n-1)

C  またはこれを逆に行います。
   a(k:m+2:-1) = b(n-1:1:-1)

ユーザーは直感的に、配列 b が今度は配列 c のようになることを期待しますが、実際
の結果は予測できません。

overindex フラグは配列構文式には適用されないため、xalias=overindex フラグを使用してもこの状況は修正されません。この例をコンパイルすることはできますが、生成されたコードからは正しい結果を得られません。この例を書き換えて、配列構文を等価な DO ループに置き換えると、-xalias=overindex を使用してコンパイルしたときにこのフラグが働くようになります。しかし、このようなプログラミングはそもそも避けるべきです。