コンテンツに飛ぶ | ナビゲーションに飛ぶ

  • 日本語
  • English
 

seca


付録                               目次へ
   プログラム例「円周率πの任意長の計算」
   数値型組込み関数の主なもの
   編集記述子の主なもの
   説明を省いた主なキーワード 付録A) プログラム例「円周率πの任意長の計算」プログラム  すでに例題6_5で任意桁の実数の計算例(自然対数の底eの値)を扱ったが,ここ では公式 π = 32 Arctan(1/10) - 4 Arctan(1/239) - 16 Arctan(1/515) を用いて円周率を計算してみよう。例題6_5では,アルゴリズムをわかりやすくする ために,小数点以下各位の数字1桁ずつを整数配列要素としてプログラムしたが,こ こでは計算効率を上げるために,小数点以下5桁ずつに区切り,配列要素にする。 (1) 10進法が100000進法になるだけで原理は全く同じであるが,まず「M進法」の四則  演算を繰り上がり,繰り下がりのある配列演算として用意しなければならない。  すなおにサブルーチンにしてもよいが,モジュールの使用例を示すためユーザ定義  演算子にしておく。この方が引用する側のプログラムでは表現が直接的になり,わか  りやすい。配列間の四則演算 +-*/ はシステム標準で用意されているから,ここでは  代わりに「.plus.」「.minus.」「.times.」「.div.」 で表すことにしてある。ここ  で扱う数字は小数点以上が高々1桁であり,乗除算はM進法で1桁の数との掛け算,  1桁の数での割り算しか必要ではない。例題6_5で説明したように,10進数の場合に  筆算でやることを思い浮かべながらプログラムすればよい。ただし,引き算には補数  表現を用いて足し算と形を揃えてある。 (2) あとは冒頭の公式どおり,3種類のArctan関数を計算し,係数をかけて足したり  引いたりするだけである。用意しなければならない整数配列の大きさは,5桁ごとに  1要素(このため,CEILING関数=[与えられた実数値より大きい最小の整数]が用  いてある)であるが,最後の桁は切り捨て誤差が生じる可能性があるので,M進数で  1桁余分に用意する。出力に用いられている編集記述子「I6.5」は,6桁の長さに5桁  の整数を右詰で,データが短いときには前に0を埋めて記述する編集記述子である。  この代わりに「I6」と書いたらどうなるかを自分の目で確かめれば,意味が理解でき  よう。(⇒付録B参照) (3) 逆正接関数 Arctan は以下の展開公式を利用するが,これは主プログラムの中で  内部手続き関数として定義し,関数値として配列を返すようにしてある。 Arctan(1/k) = (1/k) - (1/3)(1/k)3 + (1/5)(1/k)5 - (1/7)(1/k)7 + ... +[(-1)n/(2n+1)] (1/k)2n+1 + ...  小数点以下d桁まで求めるとして,この展開の打ち切り誤差を10-d以下にするには, 以下の不等式で与えられるnまで計算すれば十分であることが評価できる。 n > (d/2)/log10 k このとき,例によって展開式を以下のように書いて,内側から計算していけばよい。 Arctan(1/k) = (1/k)[1 - (1/k2)[(1/3) - (1/k2)[(1/5) - (1/k2)[(1/7) - ... -(1/k2)[ 1/(2n+1) - 0 ]]] ... ]  桁数は任意といっても,用いたアルゴリズムによる限界がある。割り算をM進数1桁 での割り算しか用意していないから,上記の展開式中の分母の最大値 2n+1が100000を 越えてはならない。最も高次の項まで展開を必要とするk=10のときの制限により,およ そ10万桁までとなる。k=512のときには,もう一つの分母k^2が100000を越えるが,プロ グラムではkで2回割ることで限界を回避してある。 [ pi.f90 ] !===================== 円周率πの計算 ==============================! ! π = 32*Arctan(1/10) - 4*Arctan(1/239) - 16*Arctan(1/515) ! ! ========================================================================! MODULE multimal INTEGER :: mal = 10**5, prec ! INTERFACE OPERATOR(.plus.) ! .plus. = + MODULE PROCEDURE add END INTERFACE INTERFACE OPERATOR(.minus.) ! .minus. = - MODULE PROCEDURE subtract END INTERFACE INTERFACE OPERATOR(.times.) ! .times. = * MODULE PROCEDURE multiply END INTERFACE INTERFACE OPERATOR(.div.) ! .div. = / MODULE PROCEDURE divide END INTERFACE ! CONTAINS ! -------------------------------------------------------------------- FUNCTION add(x, y) RESULT(z) ! z = x + y INTEGER, INTENT(IN) :: x(0:prec), y(0:prec) INTEGER :: z(0:prec), i, zi, r r = 0 DO i = prec, 0, -1 zi = x(i) + y(i) + r r = zi/mal ! 繰り上がり z(i) = zi - r*mal END DO END FUNCTION add ! -------------------------------------------------------------------- FUNCTION subtract(x, y) RESULT(z) ! z = x - y INTEGER, INTENT(IN) :: x(0:prec), y(0:prec) INTEGER :: z(0:prec), i, zi, r r = 1 DO i = prec, 0, -1 zi = x(i) + (mal - 1 - y(i)) + r r = zi/mal ! 繰り上がり z(i) = zi - r*mal END DO END FUNCTION subtract ! -------------------------------------------------------------------- FUNCTION multiply(x, s) RESULT(z) ! z = x * s INTEGER, INTENT(IN) :: x(0:prec), s INTEGER :: z(0:prec), i, r, zi r = 0 DO i = prec, 0, -1 zi = x(i)*s + r r = zi/mal ! 繰り上がり z(i) = zi - r*mal END DO END FUNCTION multiply ! -------------------------------------------------------------------- FUNCTION divide(x, s) RESULT(z) ! z = x / s INTEGER, INTENT(IN) :: x(0:prec), s INTEGER :: z(0:prec), i, r, zi r = 0 DO i = 0, prec zi = x(i) + r*mal z(i) = zi/s r = zi - s*z(i) ! 剰り END DO END FUNCTION divide END MODULE multimal ! ======================================================================== PROGRAM pi_main !!! Main Program USE multimal INTEGER :: digit INTEGER, ALLOCATABLE :: pi(:) ! PRINT *," How many digits? (0 < digit < 100,000): " READ*, digit prec = CEILING(digit/5.0) + 1 ALLOCATE( pi(0:prec) ) ! pi = (arctan( 10) .times. 32) & .minus. (arctan(239) .times. 4) & .minus. (arctan(515) .times. 16) ! PRINT "(20X, '***** πの計算 ( ', I6, ' 桁 ) *****')", digit PRINT "(' π = 3.', I5.5, 9I6.5/(7X, 10I6.5))", pi(1:prec-1) CONTAINS ! -------------------------------------------------------------------- FUNCTION arctan(k) RESULT(a) !!! a = Arctan(1/k) INTEGER, INTENT(IN) :: k INTEGER :: a(0:prec), unity(0:prec), n unity = (/ 1, (0, n = 1, prec) /) ! unity = 1.00000 00000... a = 0 DO n = INT( 0.5*digit/LOG10(REAL(k)) )+1, 1, -1 a = (((unity .div.(2*n+1)) .minus. a) .div. k) .div. k END DO a = (unity .minus. a) .div. k ! for n = 0 END FUNCTION arctan END PROGRAM pi_main (実行例) How many digitst? (0 < digit < 100,000): 1000 ***** πの計算 ( 1000 桁 ) ***** π = 3.14159 26535 89793 23846 26433 83279 50288 41971 69399 37510 58209 74944 59230 78164 06286 20899 86280 34825 34211 70679 82148 08651 32823 06647 09384 46095 50582 23172 53594 08128 48111 74502 84102 70193 85211 05559 64462 29489 54930 38196 44288 10975 66593 34461 28475 64823 37867 83165 27120 19091 45648 56692 34603 48610 45432 66482 13393 60726 02491 41273 72458 70066 06315 58817 48815 20920 96282 92540 91715 36436 78925 90360 01133 05305 48820 46652 13841 46951 94151 16094 33057 27036 57595 91953 09218 61173 81932 61179 31051 18548 07446 23799 62749 56735 18857 52724 89122 79381 83011 94912 98336 73362 44065 66430 86021 39494 63952 24737 19070 21798 60943 70277 05392 17176 29317 67523 84674 81846 76694 05132 00056 81271 45263 56082 77857 71342 75778 96091 73637 17872 14684 40901 22495 34301 46549 58537 10507 92279 68925 89235 42019 95611 21290 21960 86403 44181 59813 62977 47713 09960 51870 72113 49999 99837 29780 49951 05973 17328 16096 31859 50244 59455 34690 83026 42522 30825 33446 85035 26193 11881 71010 00313 78387 52886 58753 32083 81420 61717 76691 47303 59825 34904 28755 46873 11595 62863 88235 37875 93751 95778 18577 80532 17122 68066 13001 92787 66111 95909 21642 01989 (付録B)数値型組込み関数の主なもの 先頭へ  3章3.3.では総称名だけを並べたが,ここでは関数そのものが型を持つ個別名も あわせてまとめておく。総称名では,引数の型によって自動的に関数の型が決まる のに対して,個別名では引数の型と関数の型の双方が決められており,関数名を 副プログラム引用の引数に書く場合には型をもつ個別名が使われる。なお,総称名 の場合でも,型変換に関する関数のように引数の型と関数の型が異なるものは, 以下の表に個別名の欄を空欄にして並べてある。  ABS ACOS AIMAG AINT ASIN ATAN ATAN2  CEILING CMPLX CONJG COSH  DBLE  EXP  FLOOR  INT  LOG LOG10  MAX MIN MOD MODULO  NINT  REAL  SIGN SIN SINH SQRT  TAN TANH      備考「拡張」:標準仕様にはないもの。       「×」 :実引数に書くことができないもの ABS(x):絶対値 先頭へ    個別名      引数の型      関数の型     備考 --------------------------------------------------------------------- IABS INTEGER(4) INTEGER(4) ABS REAL(4) REAL(4) DABS REAL(8) REAL(8) CABS COMPLEX(4) REAL(4) ACOS(x):逆余弦関数 先頭へ    個別名      引数の型      関数の型     備考 --------------------------------------------------------------------- ACOS REAL(4) REAL(4) DACOS REAL(8) REAL(8) AIMAG(z):複素数の実数部 先頭へ    個別名      引数の型      関数の型     備考 --------------------------------------------------------------------- AIMAG COMPLEX(4) REAL(4) DIMAG COMPLEX(8) REAL(8) 拡張 AINT(x):実数の整数部分 先頭へ    個別名      引数の型      関数の型     備考 --------------------------------------------------------------------- AINT REAL(4) REAL(4) DINT REAL(8) REAL(8) ANINT(x):実数の四捨五入 先頭へ    個別名      引数の型      関数の型     備考 --------------------------------------------------------------------- ANINT REAL(4) REAL(4) DNINT REAL(8) REAL(8) ASIN(x):逆正弦関数 先頭へ    個別名      引数の型      関数の型     備考 --------------------------------------------------------------------- ASIN REAL(4) REAL(4) DASIN REAL(8) REAL(8) ATAN(x):逆正接関数 先頭へ    個別名      引数の型      関数の型     備考 --------------------------------------------------------------------- ATAN REAL(4) REAL(4) DATAN REAL(8) REAL(8) ATAN2(y,x):逆正接関数 arctan(y/x) 先頭へ    個別名      引数の型      関数の型     備考 --------------------------------------------------------------------- ATAN2 REAL(4) REAL(4) DATAN2 REAL(8) REAL(8) CEILING(x):x以上で最小の整数 先頭へ    個別名      引数の型      関数の型     備考 --------------------------------------------------------------------- REAL(4) INTEGER(4) CMPLX(x[, y][, KIND]):複素数の構成 先頭へ    個別名      引数の型      関数の型     備考 --------------------------------------------------------------------- REAL(4) COMPLEX(4) COMPLEX(4) COMPLEX(4) CONJG(z):共役複素数 先頭へ    個別名      引数の型      関数の型     備考 --------------------------------------------------------------------- CONJG COMPLEX(4) COMPLEX(4) DCONJG COMPLEX(8) COMPLEX(8) COSH(x):双曲余弦関数 先頭へ    個別名      引数の型      関数の型     備考 --------------------------------------------------------------------- COSH REAL(4) REAL(4) DCOSH REAL(8) REAL(8) DBLE(x):倍精度実数化,引数が複素数の場合には実数部 先頭へ    個別名      引数の型      関数の型     備考 --------------------------------------------------------------------- INTEGER(4) REAL(8) REAL(8) REAL(8) COMPLEX(4) REAL(8) COMPLEX(8) REAL(8) DBLE REAL(4) REAL(8) 拡張 DBLEQ REAL(16) REAL(8) 拡張 EXP(x):指数関数 先頭へ    個別名      引数の型      関数の型     備考 --------------------------------------------------------------------- EXP REAL(4) REAL(4) DEXP REAL(8) REAL(8) CEXP COMPLEX(4) COMPLEX(4) CDEXP COMPLEX(8) COMPLEX(8) 拡張 FLOOR(x):xを越えない最大の整数 先頭へ    個別名      引数の型      関数の型     備考 --------------------------------------------------------------------- REAL(4) INTEGER(4) (参考) FLOOR(3.14)=3, FLOOR(-10.5)=-11 INT(x):整数化(小数点以下切り捨て) 先頭へ    個別名      引数の型      関数の型     備考 --------------------------------------------------------------------- INT REAL(4) INTEGER(4)    × IDINT REAL(8) INTEGER(4)    × LOG(x):自然対数 先頭へ    個別名      引数の型      関数の型     備考 --------------------------------------------------------------------- ALOG REAL(4) REAL(4) DLOG REAL(8) REAL(8) CLOG COMPLEX(4) COMPLEX(4) CDLOG COMPLEX(8) COMPLEX(8) 拡張 LOG10(x):常用対数 先頭へ    個別名      引数の型      関数の型     備考 --------------------------------------------------------------------- ALOG10 REAL(4) REAL(4) DALOG10 REAL(8) REAL(8) MAX(x1,x2,...):最大値 先頭へ    個別名      引数の型      関数の型     備考 --------------------------------------------------------------------- MAX0 INTEGER(4) INTEGER(4) × AMAX0 INTEGER(4) REAL(4) × MAX1 REAL(4) INTEGER(4) × AMAX1 REAL(4) REAL(4) × DMAX1 REAL(8) REAL(8) × MIN(x1,x2,...):最小値 先頭へ    個別名      引数の型      関数の型     備考 --------------------------------------------------------------------- MIN0 INTEGER(4) INTEGER(4) × AMIN0 INTEGER(4) REAL(4) × MIN1 REAL(4) INTEGER(4) × AMIN1 REAL(4) REAL(4) × DMIN1 REAL(8) REAL(8) × MOD(x,y):xをyで割った剰り( x-INT(x/y)*y ) 先頭へ    個別名      引数の型      関数の型     備考 --------------------------------------------------------------------- MOD INTEGER(4) INTEGER(4) AMOD REAL(4) REAL(4) DMOD REAL(8) REAL(8) (参考) MOD(9,5)=4, MOD(9,-5)=4, MOD(-9, 5)=-4, MOD(-9,-5)=-4 MODULO(x,y):yを法とする剰余( x-FLOOR(REAL(x)/REAL(y))*y ) 先頭へ    個別名      引数の型      関数の型     備考 --------------------------------------------------------------------- INTEGER(4) INTEGER(4) REAL(4) REAL(4) REAL(8) REAL(8) (参考)MODULO(9,5)=4, MODULO(9,-5)=-1, MODULO(-9,5)=1, MODULO(-9,-5)=-4 NINT(x):四捨五入して整数化 先頭へ    個別名      引数の型      関数の型     備考 --------------------------------------------------------------------- NINT REAL(4) INTEGER(4) IDNINT REAL(8) INTEGR(4) REAL(x):実数化,引数が複素数の場合は実数部 先頭へ    個別名      引数の型      関数の型     備考 --------------------------------------------------------------------- REAL(4) REAL(4) COMPLEX(4) REAL(4) COMPLEX(8) REAL(8) REAL INTEGER(4) REAL(4)      × FLOAT INTEGER(4) REAL(4)      × SNGL REAL(8) REAL(4)      × SIGN(x,y):xの絶対値にyの符号を付けたものを返す 先頭へ    個別名      引数の型      関数の型     備考 --------------------------------------------------------------------- ISIGN INTEGER(4) INTEGER(4) SIGN REAL(4) REAL(4) DSIGN REAL(8) REAL(8) SIN(x):正弦関数 先頭へ   個別名      引数の型      関数の型     備考 --------------------------------------------------------------------- SIN REAL(4) REAL(4) DSIN REAL(8) REAL(8) CSIN COMPLEX(4) COMPLEX(4) CDSIN COMPLEX(8) COMPLEX(8) 拡張 SINH(x):双曲正弦関数 先頭へ    個別名      引数の型      関数の型     備考 --------------------------------------------------------------------- SINH REAL(4) REAL(4) DSINH REAL(8) REAL(8) SQRT(x):平方根 先頭へ    個別名      引数の型      関数の型     備考 --------------------------------------------------------------------- SQRT REAL(4) REAL(4) DSQRT REAL(8) REAL(8) CSQRT COMPLEX(4) COMPLEX(4) CDSQRT COMPLEX(8) COMPLEX(8) 拡張 TAN(x):正接関数 先頭へ    個別名      引数の型      関数の型     備考 --------------------------------------------------------------------- TAN REAL(4) REAL(4) DTAN REAL(8) REAL(8) TANH(x):双曲正接関数 先頭へ    個別名      引数の型      関数の型     備考 --------------------------------------------------------------------- TANH REAL(4) REAL(4) DTANH REAL(8) REAL(8) (命名規則一般)以上のほかに拡張機能が用意されている場合は,      INTEGER(2) は先頭に I, INTEGER(8) は K, 4倍精度は Q を付けるようになっている。(例 IISIGN,KISIGN,QTAN など) (付録C) 主な編集記述子 先頭へ (1) データ編集記述子  以下でパラメータ w,d,m,r は次の意味で用いられる。   w:記述欄の桁数(欄の幅)   d:実数の場合,小数点からうしろの桁数 m:整数の場合,実際に数字を書く桁数   r:繰返し回数(r=1 は省略可能)  なお数値データの場合,記述欄が不足するときには ******* 印が出力される。 (整数型)  Iw[.m] 10進整数をw桁の欄に右詰で記述する。mが指定された場合,数字が短ければ      0を埋める。(例 123 を I7.5 で記述→__00123,__は空白2つ) Bw[.m] 整数を2進数型で入出力(入力定数は2進型でなければならない) Ow[.m]  〃 8進数   〃  ( 〃   8     〃     ) Zw[.m]  〃 16進数  〃  ( 〃   16    〃      ) (実数型)  Fw.d  実数値をw桁の欄に小数点以下d桁の精度で記述する。 Ew.d 指数形式で記述する。出力では仮数部の絶対値が0.1から1.0の間になる。 Dw.d     〃    (倍精度実数)  Gw.d  絶対値の大きさによって,F型とE型を使い分ける  ENw.d 工学表記指数。出力では指数が3の倍数,仮数部の絶対値が1から1000の間に      なる。  ESw.d  理学表記指数。出力では仮数部の絶対値が1桁になる。 (複素数型)  複素数1個に対して,実数型を2つ分用意すればよい。(例 2F10.7) (論理型)  Lw   先頭の文字が「.T」「T」「.t」「t」 のいずれかであれば.TRUE.,「.F」      「F」「.f」「f」 のいずれかであれば.FALSE. とみなす。(入力)      w桁の欄にTまたはFを右詰で書く。(出力) (文字型)  A[w]  w桁に書かれた文字を右から,対応する文字変数の長さ分だけ読む。変数の      長さが長いときには先頭からw文字分に代入される。(入力)      w桁の欄に右詰で書く。欄が足りないときには先頭のw文字,wが省略されて      おれば,対応する文字列の長さの欄に書く。(出力) (2) 制御編集記述子   以下でnは正整数,kは正負の整数で,n=1,k=1も省略できない。 kP 小数点を左へk桁ずらせて読み込む。(入力)        〃 右へ  〃   書く。(出力)  Tn   n桁目から入出力。(例 PRINT "(T7, 'FGHIJ', T2, 'ABCDE')" で      2桁目から ABCDEFGHIJ と書かれる。)  TLn   現在位置から左へn桁の位置から読む(または書く)。  TRn     〃   右へ   〃  nX n桁右へスキップする。  [r]/  記録の区切りを示し,出力では改行される。rのない/ の前後には区切りの     「,」は不要。  :   これ以降に入出力リストがなければ,書式を終了する。      例 PRINT "(' I=', I3, ', J=', I3)", 35 → I= 35, J = PRINT "(' I=', I3, :, ', J=', I3)", 49 → I= 49   $(または  ) 改行しない。[拡張機能] (3) 文字定数記述子  以下の3通りの書き方がある。   '文字列' "文字列" nH文字列 (nは文字数)  [廃止予定] (4) 変数書式 [拡張機能]  上記の編集記述子に現れた定数 w,d,m,r,n を,整数変数で指定する方法である。 これ等の定数を書く位置に,< >で囲んだ <整数変数式> の形を書くことが できる。ただし,文字列形式の書式では演算式を含む形は許されず,<整数変数> のみである。(注:DVFのVer.6では文字列書式でも使用可能になったようである。)   例 FORMAT(1X, <n>F10.<n-1>, I<MAX(5,n)> ) 注)先頭の1文字について
以上では「出力の際に,システムによって行の先頭の1文字は行制御専用に予約 され,印字されない」ことを考慮していない。これが適用されるシステムでは, 「Tn」などの意味を1桁修正する必要がある。 付録D説明を省いた主なキーワード 先頭へ ACCESS, ACTION, ASSIGN, BIT_SIZE, BLANK, BLOCK DATA, BN型, BZ型, BTEST, B形, CEILING, COMMON, DBLE, DELIM, DIGITS, DIRECT, DOT_PRODUCT, DPROD, D形, ENTRY, EN形, EPSILON, ES形, EXIST, EXPONENT, FLOOR, FORMATTED, FRACTION, G形, HUGE, IBCLR, IBITS, IBSET, INQUIRE, LBOUND, LGE, LGT, LLE, LLT, L形, MAXEXPONENT, MERGE, MINEXPONENT, MODULO, MVBITS, NAMED, NAMELIST, NAME, NEAREST, NEXTREC, NML, OPENED, O形, PAC, PAD, PAUSE, POSITION, PRIVATE, PUBLIC, P形, RADIX, RANDOM_SEED, READWRITE, RECL, REC, RRSPACING, SCALE, SEQUENCIAL, SET_EXPONENT, SYSTEM_CLOCK, S形 TINY, TRANSFER, T形, UBOUND, UNFORMATTED, X形, Z形  この他にも,組込み関数や組込みサブルーチンが多数ある。これらの全てを覚えて いなくて,もし同じ名前の英字名をプログラム中で使ったとしても,何ら支障は起き ない。(→1.3.3.) (おわり)目次へ