2010-12-17 3 views
2

以下のコードは正常に実行されます。それが本当に正しいのだろうか?C#4.0 Parallel.ForEach内からのフォームコントロールへのアクセス

if (openFileDialog.ShowDialog() == DialogResult.OK) 
{ 
    Parallel.ForEach(openFileDialog.FileNames, currentFile => 
    { 
     try 
     { 
      StreamReader FileReader = new StreamReader(currentFile); 
      do 
      { 
       URLtextBox.Invoke(new MethodInvoker(delegate 
       { 
        URLtextBox.Text += SelectURLfromString(FileReader.ReadLine()); 
       })); 
      } 
      while (FileReader.Peek() != -1); 
      FileReader.Close(); 
     } 
     catch (System.Security.SecurityException ex) 
     { 
      ... 
     } 
     catch (Exception ex) 
     { 
      ... 
     } 
    }); 
} 

は、そうでなければ、私はどちらかを取得「クロススレッド操作ではない有効な。別のスレッドからアクセスコントロール 『URLtextBox』」やスタックのアプリケーション。

答えて

5

コードが正しいかを見てみましょう。しかし、あなたにもGUIスレッドでSelectURLfromString(FileReader.ReadLine());方法をexcutingている、あなたは

string url = SelectURLfromString(FileReader.ReadLine()); 
    URLtextBox.Invoke(new MethodInvoker(delegate 
    { 
     URLtextBox.Text += url; 
    })); 

によって最小限にGUIスレッドで作業を最小限に抑えることを交換する必要があります。

1

コントロールは関連するUser32ウィンドウ(多くの場合、HWNDと呼ばれています)を作成したスレッドにバインドされているため、呼び出しが必要です。つまり、Invokeのデリゲートの外にあるファイルの内容を読み込んで処理することで、少しは最適化することができます。

2

コードは正しく、GUIスレッドでコントロールが更新されるようにInvokeコールが必要です。あなたが平行でないリソースを使用している並列処理を行っている

  • はしかし、実際にコードに意味がありませんいくつかの他のものがあります。あなたのスレッドはディスクからの注意のために戦っています。これは明らかに速度が遅いためボトルネックです。

  • 複数のファイルから行を読み込み、それらをテキストボックスに混在させてダンプします。この特定の状況では問題ないかもしれませんが、一般的に予測できない結果をもたらします。

  • 文字列を連結するには、+=操作を使用しています。この方法は、スケーラビリティが悪いことで有名です。この場合は大きな問題ではないかもしれませんが、ディスクボトルネックがおそらくもっと悪いです。

+0

ああ、素敵な発言!ありがとう。 – 84RR1573R

関連する問題