1

最新のOO機能を学習するためにFortran、のバージョンFortranが作成され、以下にリンクされています()。ソースは1つを模倣します。DelphiTStringListgist.githubFortranDelphi

これFortran TStringListは期待どおりに機能します。ただし、私の問題は、30MBのファイルを読み書きするためのLoadFromFile / SaveToFileの組み合わせが、Delphiの対応するファイルよりも10倍遅いことです。ファイルが大きいほど、Fortranのバージョンは見栄えが悪くなります。私のアマチュアFortranスキルのおかげで、私は驚かないでしょう。同じ理由で、パフォーマンスの低下がどこで発生するのか、どこから始めればよいのかさえ理解できませんでした。コメントをお願いします。どうもありがとうございました!

System.f90

SysUtils.f90

Classes_TStringList.f90

LoadFromFile/SaveToFileのテストプログラム

4

1 に答える 1

3

最も根本的な違いは、Delphi の「文字列」型と Fortran-90 の可変長文字列の性質の違いによるものだと思います。

Delphi では、文字列は参照型です。それだけでなく、参照カウントとコピーオンモディファイ タイプでもあります。

それはあなたが書くときです:

  var
    a, b: String;   
  begin
    a := 'The quick brown fox';
    b := a;

    b := b + ' jumped over the lazy dog.';
  end;

aがbに割り当てられている場合、文字列の文字はコピーされません。代わりに、 baは、参照カウント 2 で同じ文字列を参照するポインターになります。

次にbが変更されると、その時点でのみ、独自の参照カウント (1) を持つ最初の複製文字列を作成し、元の参照カウントをデクリメントするために必要なコードが (コンパイラによって) 生成されます。

ただし、文字列をリストに追加するだけでは明らかに変更されません。

TStringListがファイルの内容を読み取る場合、ファイルから文字列が読み取られます。次に文字列値が内部リストに追加されると、文字列自体はコピーされず、代わりに参照カウントが増加するだけです。これは、「LoadFromFile」メソッドがその文字列を使用しなくなった場合でも (その内容が既に使用されているため)、その事実を反映しています。ファイルから読み取られた次の文字列に置き換えられます) 以前に内部リスト項目に追加されたものは有効なままです。

次に、 LoadFromFileは、ファイルから次の文字列を受け取る準備ができている新しい文字列を初期化する必要がありますが、これは避けられません。

違いは、Fortran バージョンでは、ファイルから読み取られるときに各文字列を初期化することに加えて、項目がリストに追加される時点でそれらの文字列のそれぞれもコピーする必要があることです。この文字列データのコピーは、参照カウント文字列型のおかげで、Delphi コードでは排除されています。

したがって、Fortran コードの効率が低下することは避けられません。また、Delphi における参照カウント型の String 型の効率の向上は、定義と設計により、この文字列型のヘビー「ユーザー」であるクラスのほぼすべての領域に影響を与えます。 .

これは、Delphi コンパイラと Fortran のメモリ管理のパフォーマンスまたはコード生成効率の相対的な違いに加えて、さらに大きくなります。

于 2012-07-08T21:31:48.050 に答える