2011-05-19 5 views
5

私はDirectory.GetFilesを使って私にmp3ファイルを与えています。ListBoxに結果を記入したいのですが、メソッドを実行中にプログラムを停止する代わりに、ListBoxを検索して入力してくださいそれはmp3ファイルを取得するように?directory.GetFiles、どのように見つけてアイテムを吐き出すのですか?

ので、私は何を使っていることは、次の通りである(そしてそれらを一度に1つずつを追加するために失敗している、それが行われたときには、一度にすべてを追加している)

private List<string> Getmp3sFromFolders(string folder) 
    { 
     List<string> fileArray = new List<string>(); 

     try 
     { 
      DirectoryInfo dir = new DirectoryInfo(folder); 
      var files = dir.EnumerateFiles("*.mp3"); 
      foreach (var file in files) 
      { 

       fileArray.Add(file.FullName); 
       Dispatcher.BeginInvoke(_AddMP3ToListbox, file.Name); 
      } 

      var directories = dir.EnumerateDirectories(); 
      foreach (var subdir in directories) 
      { 
       fileArray.AddRange(Getmp3sFromFolders(subdir.FullName)); 

      } 

      // lblFolderSearching.Content = folder.ToString(); 
     } 
     catch 
     { 

     } 
     return fileArray; 
    } 

私は_AddMP3ToListbox = AddMP3ToListbox

を追加しました

mp3を実際にリストボックスに追加しますが、見つけたらすぐにすべてを一度に行います。どうすればこの問題を解決できますか?

答えて

11

Directory.GetFilesの代わりにDirectory.EnumerateFilesを使用してください。 EnumerateFilesは、システムが見つけたファイルを返します。すべてのファイルが見つかるまで待機しません。

これをバックグラウンドスレッドで行い、それぞれがListBoxに追加されるように、UIスレッドにDispatcher.InvokeまたはDispatcher.BeginInvokeを使用します。

私が一緒に投げた簡単な例です。ここではXAMLです:

<Window x:Class="WpfApplication1.MainWindow" 
     xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" 
     xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" 
     Title="MainWindow" Height="350" Width="525"> 
    <Grid> 
     <Grid.RowDefinitions> 
      <RowDefinition Height="*" /> 
      <RowDefinition Height="Auto" /> 
     </Grid.RowDefinitions> 
     <ListBox x:Name="_FileList" /> 
     <Button Grid.Row="1" Content="Go!" Click="Button_Click" /> 
    </Grid> 
</Window> 

、ここビハインドコードは次のとおりです。

using System; 
using System.IO; 
using System.Windows; 

namespace WpfApplication1 
{ 
    /// <summary> 
    /// Interaction logic for MainWindow.xaml 
    /// </summary> 
    public partial class MainWindow : Window 
    { 
     private Action<string> _AddToListBox; 

     public MainWindow() 
     { 
      InitializeComponent(); 
      _AddToListBox = AddToListBox; 
     } 

     private void Button_Click(object sender, RoutedEventArgs e) 
     { 
      Action action = Go; 
      action.BeginInvoke(null, null); 
     } 

     private void Go() 
     { 
      foreach (var file in Directory.EnumerateFiles(@"c:\windows\system32\")) 
      { 
       Dispatcher.BeginInvoke(_AddToListBox, file); 
      } 
     } 

     private void AddToListBox(string toAdd) 
     { 
      _FileList.Items.Add(toAdd); 
     } 
    } 
} 

決してこれがベスト・プラクティス、またはすべての包括的な例であるために、私はつもりです。ちょうどあなたにそれを行う一つの方法を示しています。ちなみに、system32ディレクトリにはファイルがたくさんあるので、私はそれをテストすることができます。私のマシンではまだほとんど瞬時に動作します。

+0

クールで、彼らがEnumerateFilesを追加したことはわかりませんでした。 –

+0

はい。私は最近まで知らなかった。それもSilverlightにあります。物事を非同期化するためには間違いなく便利です。 – Tim

+0

リストボックスに出力するサンプルコードをC#で教えてもらえますか?私はそれを試して、私はGetFilesより遅い時間を得ています – darthwillard

関連する問題