17

大きなTXTファイルサイズを読みたい 500 MB, 最初に使用

var file = new StreamReader(_filePath).ReadToEnd();  
var lines = file.Split(new[] { '\n' });

しかし、それはメモリ例外をスローし、行ごとに読み取ろうとしましたが、約150万行を読み取った後、メモリ例外をスローします

  using (StreamReader r = new StreamReader(_filePath))
         {            
             while ((line = r.ReadLine()) != null)            
                 _lines.Add(line);            
         }

または私が使用した

  foreach (var l in File.ReadLines(_filePath))
            {
                _lines.Add(l);
            }

しかし、再び私は受け取った

タイプ 'System.OutOfMemoryException' の例外が mscorlib.dll で発生しましたが、ユーザー コードで処理されませんでした

私のマシンは 8GB の RAM を搭載した強力なマシンなので、私のマシンの問題ではありません。

ps: このファイルを NotePadd++ で開こうとしたところ、「ファイルが大きすぎて開けません」という例外が発生しました。

4

5 に答える 5

38

File.ReadLinesを使用するだけで、を返し、IEnumerable<string>すべての行を一度にメモリにロードしません。

foreach (var line in File.ReadLines(_filePath))
{
    //Don't put "line" into a list or collection.
    //Just make your processing on it.
}
于 2012-11-16T12:02:00.643 に答える
4

例外の原因は、_lines コレクションが増えているようですが、大きなファイルを読み取っていないようです。行とを読んでいadding to some collection _lines which will be taking memory and causing out of memory execptionます。フィルターを適用して、必要な行のみを _lines コレクションに入れることができます。

于 2012-11-16T11:45:11.350 に答える
1

編集:

ファイル全体をメモリにロードすると、オブジェクトが大きくなり、オブジェクトに十分な連続メモリを割り当てることができない場合、.net は OOM 例外をスローします。

答えは同じです。コンテンツ全体を読み取るのではなく、ファイルをストリーミングする必要があります。これには、アプリケーションの再構築が必要になる場合がありますが、IEnumerable<>メソッドを使用すると、アプリケーションのさまざまな領域でビジネス プロセスを積み重ねて、処理を遅らせることができます。


8 GB の RAM を搭載した「強力な」マシンは、500 GB のファイルをメモリに保存することはできません。 '.Net にすべてのメモリを割り当てないでください。32 ビットには 2GB の制限があり、ファイルを開いて行を格納するとデータが 2 回保持され、オブジェクト サイズのオーバーヘッドが発生します....)

すべてをメモリにロードして処理することはできません。処理を通じてファイルをストリーミングする必要があります。

于 2012-11-16T11:53:13.937 に答える