関連情報
ナビゲーション:Fortran 2003入門   前へ   上へ   次へ

4.1 パラメタ化構造型

Fortran 2003では構造型が型パラメタを持てるようになりました。 組込み型に対するものと同様に2種類の形で提供されます: "kind"と類似のもの (コンパイル時に既知でなくてはなりません(“kind”型パラメタと呼ばれる))と、 文字長と類似のもの(実行時に変更可能です(“length”型パラメタと呼ばれる))の2種類です。

4.1.1 基本構文とセマンティクス

型パラメタを持つ構造型はそれらを型定義で列記しなければなりません。 型を与えて“kind”パラメタもしくは“length”パラメタの指定を行います。
例:
  TYPE real_matrix(kind,n,m)
    INTEGER,KIND :: kind
    INTEGER(int64),LENGTH :: n,m

すべての型パラメタはINTEGER型として明示的に指定される必要がありますが、 整数の種別は特に何であっても構いません。 型パラメタは常にスカラで配列は許されていません。 型定義において“kind”型パラメタは定数式中で利用でき、 任意の型パラメタを宣言式(配列境界、文字長、もしくは“length”型パラメタ値)の中で使用できます。 例えば上記の型定義の残りは次のようになります:

    REAL(kind) value(n,m)
  END TYPE real_matrix

このような構造型の要素を宣言する場合には型パラメタを名前の後に指定しなければなりません。
例:

  TYPE(real_matrix(KIND(0d0),100,200)) :: my_real_matrix_variable
同様にこのような型の値を構築する際に、型パラメタを指定しなければなりません。
例:
  my_real_matrix_variable = &
    real_matrix(kind(0d0),100,200)((/ (i*1.0d0,i=1,20000) /))

型定義の外で構造型パラメタの値を調べるためには、成分を参照する場合と同様の記述が用いられます。
例:

  print *,'Columns =',my_real_matrix_variable%m
型パラメタ名は成分名や型束縛手続名と同じクラスに属しています。 しかし代入の左辺において、型パラメタをその指定子を使って変更することはできません。 そして組込み型パラメタもこの方法により調べることが可能です。例えば
  REAL :: array(:,:)
  CHARACTER(*),INTENT(IN) :: ch
  PRINT *,array%kind,ch%len
KIND(array)LEN(ch) で同じ値を出力します。 種別パラメタの調査はオブジェクトが配列であっても常にスカラである点に注意して下さい。

構造型パラメタは型定義中で必ずしも実際に使われる必要はなく、 種別型パラメタを宣言式内でのみ使用することもあり得ます。
例:

  TYPE fixed_byte(n)
    INTEGER,KIND :: n
    INTEGER(1) :: value(n)
  END TYPE
  TYPE numbered_object(object_number)
    INTEGER,LENGTH :: object_number
  END TYPE
fixed_byte パラメタ n は “kind” 型パラメタとして宣言されているので常に定数値を指定する必要があります。 同様に object_number はここでは使われていませんが、常に値を指定する必要があります。 それぞれの numbered_object はたとえそれが配列であっても object_number に対する一つの値を持ちます。

4.1.2 セマンティクスの追加説明

型パラメタを持つ構造型はデフォルト値を持つことが可能です。 この場合デフォルト値を持つパラメタは型指定子で省略が可能です。
例:
  TYPE char_with_maxlen(maxlen,kind)
    INTEGER,LENGTH :: maxlen = 254
    INTEGER,KIND   :: kind = SELECTED_CHAR_KIND('ascii')
    INTEGER        :: len = 0
    CHARACTER(len=maxlen,kind=kind) :: value
  END TYPE
  ...
  TYPE(char_with_maxlen) temp
  TYPE(char_with_maxlen(80)) card(1000)
  TYPE(char_with_maxlen(kind=SELECTED_CHAR_KIND('iso 10646'))) ucs4_temp

種別型パラメタは定数式中で使えます(従ってデフォルトの初期化で使えます)が、 大きさが可変である成分は長さの型パラメタに依存するためデフォルトによる初期化は行えません。 従って上記例の value はデフォルト初期化できません。

組込み型とは異なり、構造型代入においては異なる型パラメタ値間での自動的な変換はありません。 そのため上記の宣言が行われています。

  card(1) = card(2) ! This is ok, maxlen==80 for both sides.
  temp = card       ! This is not allowed - maxlen 254 vs. maxlen 80.

4.1.3 引継ぎ型パラメタ

構造型の引継ぎ型パラメタは、仮引数でのみ認められていて名前付き定数では認められていません。 例えば次のサブルーチンは任意の char_with_maxlen 変数に対して機能しま す。
  SUBROUTINE stars(x)
    TYPE(char_with_maxlen(*)) x
    x%value = REPEAT('*',x%maxlen)
  END SUBROUTINE

4.1.4 無指定型パラメタ

無指定型パラメタはFortran 2003での新機能です。これらは CHARACTER と パラメタ化構造型の両方で利用可能で、無指定配列境界と同じような動作をします。 無指定型パラメタを持つ変数は ALLOCATABLE もしくは POINTER 属性を持つ必要があります。 割付け変数の無指定型パラメタの値は割付け(型付き割付けもしくは組込み代入の 自動再割付け)により決定されます。 ポインタにおいては、無指定型パラメタの値は指示先の型パラメタの値となります。 次は上記で定義されている型 real_matrix を使った例です。
  TYPE(real_matrix(KIND(0.0),100,200)),TARGET :: x
  TYPE(real_matrix(KIND(0.0),:,:)),POINTER :: y, z
  ALLOCATE(real_matrix(KIND(0.0),33,44) :: y)  ! Typed allocation.
  z => x                                       ! Assumes from the target.
  PRINT *,y%n,z%n                              ! Prints 33 and 100.
割付けされていない割付け及び指示先と結合されていないポインタの 無指定型パラメタ値は参照できない点に注意して下さい。

仮引数が割付けもしくはポインタの場合、実引数は仮引数と完全に同じ無指定型パラ メタでなくてはなりません。
例:

  SUBROUTINE sub(rm_dble_ptr)
    TYPE(real_matrix(KIND(0d0),*,:)),POINTER :: rm_dble_ptr
  ...
  TYPE(real_matrix(KIND(0d0),100,200)),POINTER :: x
  TYPE(real_matrix(KIND(0d0),100,:)),POINTER :: y
  TYPE(real_matrix(KIND(0d0),:,:)),POINTER :: z
  CALL sub(x)  ! Invalid - X%M is not deferred (but must be).
  CALL sub(y)  ! This is ok.
  CALL sub(z)  ! Invalid - X%N is deferred (but must not be).


Results matter. Trust NAG.
Privacy Policy | Trademarks