パラメーター ストレージ クラス

パラメーターは、その引数と記憶域を共有します。そのため、ストレージ クラスは、最終的には関連する引数のクラスによって決定されます。技術的には、パラメーター変数自体は、対応する引数のアドレスを含む AUTOMATIC 変数です。便宜上、パラメーターは、別個の「パラメーター」ストレージ クラスを持つと見なすこともできます。次に例を示します。

DECLARE X FLOAT; 
CALL P (X);
   .
   .
   .
P: PROCEDURE (Y); 
      DECLARE Y FLOAT;

この例では、X は引数であり、Y はパラメーター変数です。パラメーター変数は、プロシージャの宣言内で宣言され、そのプロシージャが呼び出される際に値を受け取ります。Open PL/I の単純な変数の引数は、参照で渡されます。

パラメーターにはデータ型 (多くの場合は範囲を持つデータ型) があり、最も単純な場合、パラメーターに渡される引数はそのパラメーターと同じデータ型および範囲を持ちます。それ以外の場合でも、Open PL/I では、可能な限り、パラメーターと同じデータ型および範囲を持つ値に引数が変換され、その値がパラメーターに渡されます。

別段の指定がない限り、同じデータ型および範囲を持つパラメーターに変数が引数として渡される場合、引数は「参照で」渡されます。つまり、この値は引数として渡される実際の変数自体のアドレスとなり、パラメーターはこの変数と記憶域を共有することになります。したがって、パラメーターへの代入を行うと、実際には引数の変数自体が変更されます。

それ以外の場合、つまり、引数が、パラメーターと異なるデータ型および範囲を持つ変数である場合や、引数が、式、定数、関数参照、またはかっこで囲まれた単純な変数である場合、引数は「値で」渡されます。つまり、引数の値は前述のように変換され、一時的な場所に格納されます。この値は、引数として渡されるこの一時的な場所のアドレスです。したがって、パラメーターへの代入を行っても、呼び出し元プロシージャの変数には影響しません。

算術データの精度はそのデータ型の一部です。つまり、Float Decimal(7) の変数を Float Decimal(7) のパラメーター以外の要素に参照で渡すことはできません。宣言された文字列の長さに加え、VARYING 属性および ALIGNED 属性も、文字列変数のデータ型の一部であり、対応するパラメーターと実際の引数とで記憶域を共有するためには、そのパラメーターの属性と一致する必要があります (真の参照渡し)。ピクチャ変数は、対応するパラメーターが同じピクチャを持つ場合にのみ参照で渡すことができます。文字列以外の引数およびパラメーターの ALIGNED 属性および UNALIGNED 属性は一致する必要があります。

BYVALUE 属性は、パラメーターのアドレスではなく値がプロシージャに渡されたことを示す引数引き渡し属性です。

一定の範囲を持つ配列パラメーターは、同じ一定の範囲および同じデータ型を持つ配列引数のみに渡すことができます。パラメーター構造体は、同じサイズ、形状、およびコンポーネントのデータ型を持つ構造体またはサブ構造体のみに渡すことができます。配列引数または構造体引数を値で渡すことはできません。

ANY 属性は、パラメーターについて、対応する引数のデータ型を問わないことを指定する引数引き渡し属性です。

固定長の文字またはビット文字列パラメーターを持つプロシージャは、可変長または異なる固定長の文字列引数を使用して呼び出すことができます。このような引数はすべて値で渡されるため、実際にはパラメーターの長さに変換されます。次に例を示します。

CALL P(A,(B));

この例では、A は、対応するパラメーターと一致する場合には参照で渡され、一致しない場合には値で渡されます。B は、常に値で渡されます。

引数が、式、関数参照、組み込み関数参照、定数、かっこで囲まれた変数の参照、またはデータ型がパラメーターのデータ型と一致しない変数の参照である場合、その引数は、呼び出し元のスタック フレームの記憶域の一時ブロックにコピーされ、値で渡されることになります。呼び出し元の変数の値は、値で渡される場合には変更されません。実際には、一時記憶域のアドレスが渡され、パラメーターは一時記憶域に割り当てられた記憶域を共有します。

パラメーターの範囲は、整数定数またはアスタリスク (*) のいずれかです。パラメーターの範囲が整数定数である場合、参照で渡されるすべての引数は、同じ一定の範囲を持つ必要があります。パラメーターの範囲がアスタリスクである場合、対応する引数は、任意の値の範囲を持つことができます。後者の場合、パラメーターの範囲は対応する引数の範囲になります。次に例を示します。

DECLARE A(10) FLOAT;
DECLARE B(25) FLOAT;
   .
   .
   .
CALL P(A);
   .
   .
   .
CALL P(B);
   .
   .
   .
P: PROCEDURE(X); 
   DECLARE X(*) FLOAT;

この例の 1 番目の呼び出しでは、X の範囲は (1:10) になります。2 番目の呼び出しでは、(1:25) になります。