• 締切済み

フォートランプログラムの計算負荷について

今、フォートランで数値計算をしています。 プログラムを書き換えて走らせたところ、計算速度が非常に遅くなりました。 考えられるのは、IF文を多く使うようにしたこと、サブルーチンの呼び出し回数をふやしたなどが考えられるのですが。IF文はそれほど、計算負荷の大きいものなのでしょうか。 お願いいたします。

みんなの回答

  • jeee
  • ベストアンサー率52% (119/227)
回答No.2

コンピュータによっても異なりますが、IF文は負荷の大きい処理です。 負荷を軽減するためには、つぎのようなことを行います。 算術演算等の右辺と左辺のデータの型や大きさを同じにする。同じにしないと、通常、同じにするための命令が追加されます。 論理演算等の場合、条件の対象とするデータの特性にあわせ条件文を見直しします。 例えば、 条件Aが真のデータが20件 条件Bが真のデータが30件 条件Cが真のデータが50件 した場合、つぎの順で処理した場合 IF A ・・・ IF B ・・・ IF C ・・・ 実処理では 1番目のIFは100回 2番目のIFは80回 3番目のIFは50回 計230回条件処理を行います。 これをつぎのようにした場合 IF C ・・・ IF B ・・・ IF A ・・・ 実処理では 1番目のIFは100回 2番目のIFは50回 3番目のIFは20回 計170回となり、実処理が軽減されます。 また、 IF A OR B OR C とした場合、 OR条件では、最初に条件を満たしたら、つぎ以降条件を判断しないことがあります。(コンピュータやコンパイラで異なる場合あり) よって、つぎのように変更します。 IF C OR B OR A 他にも、コンパイラによって最適化(効率化)のオプション等があると思いますので、確かめてみてください。

  • terra5
  • ベストアンサー率34% (574/1662)
回答No.1

if等の分岐は、並列処理、パイプライン処理による高速化をかなり妨害します。 また、分岐はキャッシュのミスヒットが起きる可能性があり、これによっても速度が低下します。 計算量が多い場合は極力減らさないと速度が出ません。 サブルーチン呼び出しも、比較的重い処理になりますし、 キャッシュへのミスヒットになる可能性がでてきます。 これは言語によらず同じです。

関連するQ&A

  • JAVAでフォートランのプログラムを動かす方法

    プログラムの初心者なのですが、JAVAを使ってプログラムを作るのですがJAVAで入出力の部分を作りそこで設定した値をフォートランで作ってある計算プログラムにいれて計算させ結果をJAVAで出力することはできるのですか? 簡単に書くと 入力画面(JAVA)    ↓   計算(フォートラン)    ↓ 出力画面(JAVA) こういう感じのものができるかどうか教えてください。 宜しくお願いします。

    • ベストアンサー
    • Java
  • UNIX フォートラン 数値計算精度

    フォートランでの数値計算精度に関して困っております。 サンマイクロシステムズ社製、UNIX、Solaris10(64bit)において、 下のフォートランプログラム、 IMPLICIT REAL*8(A-H,O-Z) X=1.0D0 A=SIN(X) WRITE(*,100)A 100 FORMAT(F50.40) STOP END を実行させると、 A=0.8414709848078965048756572286947630345821 となり、16桁以降にも数値が出てきます。 これはなぜでしょうか? UNIXコンパイラの特徴なのでしょうか?

  • フォートランのサブルーチンの内部変数

    すみません。科学技術系の人間でして、フォートランが現役なのです。 あるプログラムのことですが、サブルーチンの内部の変数についてサブルーチンを呼び出すごとに加算していくようなことを行っています。 do i=1,100 call abc(i)   ← サブルーチンabcを100回呼び出す enddo end subroutine abc(i) n=n+1        ←呼び出されるたびに和をとる。 write(*,*) n return end このようなシンプルなプログラムは問題ないのですが、少し複雑になるとどういうわけか、呼び出される度にnが初期化され、writeさせた結果常に1が表示されるという現象に会いました。 昔のコンパックフォートラン(MS-Fortran, DEC Fortranを継承)と、最近のIntel Fortran(最新版)で動作が異なります。前者では和を取ってくれますが、後者では初期化されて常に1が出力されます。(上記のプログラムは問題なしです。もう少し長いプログラムでの問題です。) 言語仕様の問題(すなわちフォートランのバージョン)なのか、コンパイラ仕様の問題なのか、C言語のように宣言の仕方で変ったりするようになったというようなことはないでしょうか。 以下に示すように和をとる変数をメインプログラム側に一旦見えるようにすると、インテル版でも思ったとおりの動作をします。 call abc(i,n) suboroutine abc(i,n) としてnをメイン側に露出する。 よろしくお願いします。

  • フォートランでの相互相関関数の計算

    酒器について質問です。 ある2つのポイントで計測した実験データがあります。 その2つの実験データの間の時間のずれΔtを相互相関関数を用いて求めたいと考えています。 参考書やインターネットを通して理論は理解できるのですが、それをフォートランを用いた場合どのようにして計算させるのか分かりません。 具体的のどのようにして計算したらよいのでしょうか? どのようなプログラム文を打てばよいか教えていただきたいです。 流れとしてはデータ数1000の場合 2つのファイルをopen データ読み込み f() g() do p=-500,500 do i=1,1000 s=f(i)*g(i+p) ss=ss+s ........... のような流れになるのでしょうか? どなたか分かる方是非教えてください よろしくお願いします

  • 64ビットPCでのフォートランコンパイラ

    仕事柄いまだにフォートランのプログラムソースを書いています。物理シミュレーションを行っており、計算機の高速化に期待しているところです。地球シミュレータなどのメインフレーム?ではなく、高速のパソコンでも仕事ができるような程度のものです。 さて、質問ですが、最近、64ビットPC機、64ビット対応OSが手ごろな価格でも出ています。ノートPCでさえ8メガのメモリを積んでいるようです。この場合、フォートランコンパイラについても64ビット対応である必要があるのでしょうか。インテル、Visual Fortran, FTN95, G95, Gfortranなど有償・無償いろいろあると思います。64ビットOS用のコンパイラがあるのでしょうか。それとも従来の32ビット版でも十分な計算速度が出るでしょうか。よろしくお願いします。

  • 負荷重さの計算について

    例えば、10パイのドリルにて、周速100m、送り速度80mm/minで加工するとします。その時に掛かる負荷加重をしりたいのです。 素人ですので、上記条件はおかしいかもしれませんが、ある加工条件で加工した場合の負荷加重を知りたいのです。その計算式があれば教えてください。 ご丁寧にありがとう御座います。周速と形状は分かっているのですが、その条件にてどのくらいの重さ(kg)がかかるのか?を知りたいのです。耐圧試験機にて、材料や工具の材質などは選べませんが、試験条件の参考にしたいと考えてます。よろしくお願いします。

  • このような計算はできるでしょうか?

    現在 「2バイトの数値」から「ビットが1である数」を求める 計算を行おうと思っています。 例えば、2バイトの数値が「222」の場合 →ビットに直すと「11011110」となり →ビットが1である数は「6」となります。 この計算をVBで行いたいのですが、 効率的に行える方法はないでしょうか? AND演算を行い1ビットずつカウントすると いう方法を考えたのすが、判定の時IF文がはいってしまうため 処理速度が遅くなり、困っております。 どなたか、お気づきの方はご教授ください。

  • IF文の先のCONTINUEの意味(フォートラン)

    フォートランのプログラムコードで下記の記述を見ました。 IF( Y(5,1).LT.1) GO TO 21 21 CONTINUE この場合、CONTINUEに何らかの意味はあるのでしょうか?

  • プログラムでの配列の渡し方

    ここではフォートランの問題としてお尋ねします。(フォートランのカテゴリがないのでプログラムの専門家に聞けそうなカテゴリに質問してます。) dimension a(100,100) ... call abc(a) ... stop end subroutine abc(b) dimenison b(100,1) ... return end というようなプログラムがあります。メインの方でa(100,100)と宣言してサブルーチンではb(100,1)で受けるというような処理です。 このようにメインとサブで配列のサイズが異るのはどのようなレベルで許容されるものでしょうか。考え方がわからないのでお尋ねします。私は厳密にサイズを合わせると思っていました。しかしそうだとサブルーチンの使い回しができなくなります。このような問題はC言語の配列の先頭のアドレス云々という問題と似ているのですが。2次元配列ということがわかっていて片方のサイズがわかると自ずからもう片方のサイズがわかるということなのでしょうか。 まとめますと、以下のような点がわからないということです。 1.メインとサブで配列サイズが異なっても問題ないやり方 2.サブ側が動的に対応できるようにするプログラムの書き方(同じサブルーチンだけど、呼び出すメイン側の配列サイズに自動で対応する方法) *などを使うのだろうと思いますが。 この部分はしっかり理解しないと大怪我するところなので確認したいと思っています。 (実験して試すというのではなく、仕様としてどうかということですが) よろしくお願いします。

  • フォートランの配列の受け渡し問題

    いまどき、フォートランの配列について質問します。 配列の実引数(メイン側の配列変数)とサブルーチン側の変数(仮引数の配列変数)の受け渡しですが、配列のサイズを変動させることが可能でしょうか。 program main dimension x(100) ! xの最大配列サイズ100 .... call abc(x,np) ! 実際にはxはnp(<100)個の配列とする。   .... subroutine abc(xx,nx) ! x->xx(仮引数,配列サイズはnx=np) dimension xx(1) ! 配列の先頭を示しておく。 .... こうしておくと、サブルーチンabcで利用する配列は呼び出し側でnp(=nx,=<100)を変更することによってサイズをダイナミックに変動できると思っています。実験すると大丈夫なようです。 では、2次元、3次元の配列では配列のサイズを変数でコントロールするにはどうしたらいいでしょうか。実引数と仮引数で名前以外の変数情報を一致させるというのが教科書的な対応だと思いますが、ダイナミックに変数を変化させるにはどうしたらいいでしょうか。 追加ですが、プログラムに対して外部データを入力させる場合のnamelist入力について解説しているサイトとか本があるでしょうか。これは古臭い(フォートランでさえ古いですが、さらに古い)やり方かと思いますが、解説本には載っていないようです。 以上、よろしくお願いします。 ところで、フォートランの復権なんてことはやはりないのでしょうか。ポインタなども導入されてC言語みたいになってきているとは思いますが。