• 締切済み

fortran 渡す値について

fortranの質問です。 integer ix,iy,maxX,maxY で宣言しており、 do istep=1,100 call B_DIF(☆) do ix=0,maxX do iy=0,maxY B_M(ix,iy)=B_P(ix,iy) end do end do end do のルーチンで悩んでいます。 B_DIFは B_P(ix,iy)=K(係数のことです)*B_M(ix,iy)+B_M(ix+1,iy)-B_M(ix-1,iy) といった感じのサブルーチンです。functionで表していないのは、ややこしい関数があるので、サブルーチンでまとめてメインに返すという手法をとっています。ご了承下さい。 ここで、B_P(☆)の☆には何を入れると適切に動くと思いますか? ☆に データix,iyを入れるだけで意とするB_P(ix,iy)がでてくるのか、 それとも、ix,iy,B_Mのデータを受け渡すべきか・・ 一番の問題は、 B_P(ix,iy)=K(係数のことです)*B_M(ix,iy)+B_M(ix+1,iy)-B_M(ix-1,iy) にix,iyを送ったとき、B_M(ix+1,iy)などが意図する値を吐いてくれるのかということです。 ix=1,iy=2でB_DIFのルーチンにおいて、 B_P(1,2)=K(係数のことです)*B_M(1,2)+B_M(2,2)-B_M(0,2) とパソコンが読み取ってくれるのか疑問です。 ちなみに、B_M(1,2)、B_M(2,2)、B_M(0,2)は既知の値です。 頭がこんがらがって、どうすべきかわかりません。 2次元配列の添字の継承・・ よろしくお願いします。

みんなの回答

  • Tacosan
  • ベストアンサー率23% (3656/15482)
回答No.4

一応「common ブロックで渡す」と書いたけど, 明らかにそんなことをしない方がいいです. あとでプログラムを見たときに苦しむことが目に見えているので, 素直に引数で渡してください.

  • Tacosan
  • ベストアンサー率23% (3656/15482)
回答No.3

「B_P(☆)の☆には何を入れると適切に動くと思いますか」の B_P は B_DIF のことでしょうか? もしそうなら, 「どのような」 (what), 「どのように」 (how) 情報を渡す必要があるのかを決めることになります. まず what については, 必要な情報は K, B_P, B_M, maxX, maxY の 5つでしょうか. それはいいんですが, 次に how の方は, 思い付くのは「引数で渡す」と「common ブロックで渡す」の 2通り. どちらがお好み? あと, 配列の定義のときは副プログラムなら整合配列 (って言うんだっけ?) が使えるはずですし, メインプログラムでも (Fortran なら) allocatable 属性を付けて定義してから適当な大きさで allocate すればいいはず>#2. #1, #2 では「Fortran の勉強」と言われてますが, なんとなくこれは「Fortran の勉強」ではすまないような感じがします. もっとはっきりいうと「(言語の問題ではなく) プログラムを組めない」という感じがします.

BOY12345
質問者

補足

>思い付くのは「引数で渡す」と「common ブロックで渡す」の 2通り. どちらがお好み? 引数で渡す方が好きです。ってか前者しかできません。 common ブロックはやり方がわかりません。(テキスト読んでも??な感じでした)覚えたいとは思っているのですが・・とっかかりが無く、習得できそうな気がしません。便利だとは思うんですけどね。 commonを使ったコードあったら教えてもらえると、嬉しいです。 勉強に役立てたいと思います。

  • equinox2
  • ベストアンサー率48% (321/660)
回答No.2

前回の質問からあまり変わっていないようですが、FORTRANの文法は読まれましたか? ●do istep=1,100 のistepはどの計算で使うのですか?  この値をB_Difの中で使うのであれば渡す必要がありますが、どこにも書かれていません。 (Kの値が istep で変わる場合は istep も渡す必要あり) ●B_DIFF呼び出しの例(未検証) 関連部分のみ記載 注:maxX,maxY の値が定数なら xxxx,yyyy は maxX、maxY の値にする   変数なら、取り得る最大の値にする real*8 B_P(xxxx, yyyy) real*8 B_M(xxxx, yyyy) ・・・ call B_DIF(B_P, B_M, maxX, maxY) ・・・ subroutine B_DIFF(B_P, B_M, ixmax, iymax) real*8 B_P(xxxx, yyyy) real*8 B_M(xxxx, yyyy) do ix=0,ixmax do iy=0,iymax B_P(ix,iy)=K * B_M(ix,iy) + B_M(ix+1,iy) - B_M(ix-1,iy) end do end do ●xxxx,yyyyが大きすぎてエラーになる場合は、配列の要素毎に渡してください。  ・二次元配列の要素で計算に必要な値を渡す。  ・計算結果は1つなのでfunctionが使える B_P(ix,iy) = B_DIF( B_M(ix,iy), B_M(ix+1,iy), B_M(ix-1,iy) ) ・・・ real*8 function B_DIF(a, b, c) B_DIF = K * a + b - c return end

BOY12345
質問者

補足

●do istep=1,100 のistepはどの計算で使うのですか? すいません、書くの忘れてました。 if (mod(istep,nwrite).eq.0) then ic=ic+1 って感じで使っています。 nwrite刻みでファイル出力する形をとっています。 nwriteはintegerで定数定義しています。 上記の後に、 isen=ic/1000 ihun=mod((ic/100),10) iten=mod((ic/10),10) ione=mod(ic,10) * ofile='temp.'//char(48+isen) &//char(48+ihun)//char(48+iten)//char(48+ione) write(6,*) ic,ofile open(16,status='unknown',file=ofile) が続きます。

  • fifaile
  • ベストアンサー率25% (622/2403)
回答No.1

何がしたいのか・・・ subroutineにしてもfunctionにしても、 副関数で定めた引数を渡さないとダメですよ。 >パソコンが読み取ってくれるのか疑問です。 ためしてみました? おそらくFortranの基礎がまったくわかっていないのが問題です。 勉強しなおしてください。

BOY12345
質問者

補足

試しました。 うまく動作しない!!との事実だけがわかりました。 で、デバック作業してるんですが、、、 正直、B_P(ix+1,iy),B_P(ix,iy)とかを別途、functionで定義して、それとのやり取りをして、メインに返すのがいいのかなと思ったんですが、それだとごちゃごちゃするので、もっとスムーズに組めるのではないかと思って、皆さんに尋ねています。

関連するQ&A