Fortran77

目次

1 Fortran 77 メモ

1.1 出力の書式指定

     print 10, 'she bought ', n, 'egges.'
10   format (a20, i7, a30)
     print 20, n
20   format ('she bought ', i7, 'egges.')

これは次のようにも書ける。

print '(a20, i7, a30)', 'she bought ', n, 'egges.'
print '("she bought ",i7,"egges."), n

桁溢れは * になる

print '(f10.4,"  ",f6.3,"  ",f8.3)', 4.0/3.0, 2.0/3.0, 1234.5678
print '(f13.4,"  ",e13.4)', -12.3e20, -12.3e20
print '(a20," ",a)', 'abc', 'abcdefghi'

改行を入れるには / を入れて、改行の抑制には $ を使う

print '(a20,"  ",/,a,$)', 'abc', 'abcdefghi'
print '(a20,"  ",/,a,$)', 'ABC', 'ABCDEFGHI'

識別子を ( ) で囲って、その前に繰り返しの回数がかける。 多過ぎる識別子は無視されるので、十分大きい数(たとえば100)を与えておけば、実用上十分かも。

do i=1,n
   print '(100(f7.2))', (a(i,j),j=1,n)
end do

1.2 条件分岐

1.2.1 .true. と .false.

if (i>j .and. i>j) then
   print *, i, '>', j
else if (i==j .or. i==j) then
   print *, i, '=', j
else
   print *, i, '<', j
end if

1.3 doによる繰り返し

do i=1,5,2
   print *, i
end do

1.4 whileによる繰り返し

i=0
do while (i < 10)
   print *,i
   i=i+1
end do

1.5 配列

配列は7次元まで。各次元のサイズは 下限値:上限値で表現し、省略された下限値は1となる。

integer a(2,3,4), b(0:50), c(-1:20,5)

1.6 配列の初期化

integer x(2,3), y(2,3)
integer p, q, s, t
data p, q /1, 2/
data s /1/, t /2/
data x /1, 2, 3, 4, 5, 6/
data ((y(i,j), j=1,3), i=1,2) /1, 2, 3, 4, 5, 6/

read *, (x(i), i=1,3)

1.7 プロシージャと関数

Fortran は基本的にアドレス渡しだが、実引数に式を渡すと値渡し的に動作する。 Fortran90だけか?グローバル変数には COMMON 文を使うのだが、省略。

      program sample
      integer x,y,z(3),w(2,3)
c     関数名も型宣言が必要
      integer bar
c     文関数
      integer baz
      baz(x,y) = x**2 + y**2
      data x,y /1,2/
      data z   /10,20,30/
      data w   /11,21,31,41,51,61/
      print *,x,y
      call foo(x,y,z,3,w,2,w)
      print *,x,y
      call foo(2*x,y,z,3,w,2,w)

      print *,x,y
      x = 2
      y = bar(x)
      print *,x,y
      y = bar(7*x)
      print *,x,y

      x = 2; y = 3;
      print 10,x,y,baz(x,y)
 10   format ('baz(',i2,',',i2,')=',i2)
      stop
      end

c     配列のサイズは引数で渡せる。*で省略できたりする。整合配列
      subroutine foo(x, y, z, ldz, w, ldw,v)
      integer x, y, z(*), w(ldw,*),v(*)
      print *, 'in foo: x =', x, ', y =', y
      x = x+2; y = y+2
      print *,'z(i): ', ('z(', i, ' ) =', z(i), ', ', i=1,ldz+1)
      print *,'w(i,j): ', ((w(i,j), i=1,ldw), j=1,3)
      print *,'v(i): ', (v(i), i=1,ldw*3)
      return
      end

c     関数定義
      integer function bar(x)
      integer x
      bar = x * x
      x = 3
      return
      end
c     program end

1.8 ファイル入出力

printは出力先を変更できないので、writeを使う。

c     unit numberは0以上、99以下
      open (99, file='sec9.out')
      write (99,10) 'Hello, world!'
 10   format (a)
      close(99)

readは行単位で読むわけではない。 並べた変数の型に合わせてreadする。これはこれで便利。

open(1,file='sec9.in')
read (1,*) a, b, c
print *, a, b, c
close(1)

open(1,file='sec9.in')
read (1,*) (m(i), i=1,4)
print *, (m(i), i=1,4)
close(1)

1.9 乱数

  • rand(iflag) [0,1] の範囲の一様乱数を単精度実数で返す
  • drand(iflag) [0,1] の範囲の一様乱数を倍精度実数で返す
  • irand(iflag) [0,2147483647] の範囲の一様整数乱数を返す
      program rand_test
      implicit none
c     local:
      integer iflag/0/          ! 関数rand の引数
      integer i                 ! loop 用変数
c     function:
      real rand
      external rand             ! 教育用システムでは必要
c     begin:
      do i=1,10
	 write(*,’(I3,F9.5)’) i,rand(iflag)
      end do
      stop
      end

ここで整数引数 iflag の意味は次の通り。

  • 0 疑似乱数列の次の乱数を返す
  • 1 疑似乱数列の生成を再開し、最初の乱数を返す

その他 iflag を「種」として疑似乱数列を生成し、最初の乱数を返す

著者: OGURISU Osamu

Created: 2016-08-16 火 14:54

Emacs 24.4.1 (Org mode 8.2.10)

Validate