C#OpenFileDialog性能改进

时间:2015-05-10 09:07:46

标签: c# wpf performance parallel-processing openfiledialog

我正在装载10k到200k的文件,所以我在这里寻求一些性能提升。

我是这样做的:

        List<string> myFiles = new List<string>();
        OpenFileDialog openFileDialog = new OpenFileDialog();
        openFileDialog.Multiselect = true;
        openFileDialog.Filter = "Text files (*.txt)|*.txt|All files (*.*)|*.*";
        if (openFileDialog.ShowDialog() == true)
        {
            foreach (string filename in openFileDialog.FileNames)
            {
                myFiles.Add(filename);

            }
        }
        string[] files = myFiles.ToArray();
        Splitter(files);

        private void Splitter(string[] file)
        {
            try
            {
                tempDict = file
                    .SelectMany(i => File.ReadAllLines(i)
                    .SelectMany(line => line.Split(new[] { ' ', ',', '.', '?', '!', }, StringSplitOptions.RemoveEmptyEntries)))                    
                    .GroupBy(word => word)
                    .ToDictionary(g => g.Key, g => g.Count());
            }
            catch (Exception ex)
            {
                Ex(ex);
            }
        }

我正在考虑制作foreach pararell:

        Parallel.ForEach(openFileDialog.FileNames, filename =>
            {
                mySpam.Add(filename);
            });

安全吗?此代码中是否还有其他改进?现在,它变得迟钝,程序&#34;冻结&#34;在加载这些文件时,如果它正在做那些事情并且#34;在幕后&#34;那将是很好的。我正在使用WPF,点击按钮后开始加载文件。

2 个答案:

答案 0 :(得分:1)

嗯。您可能在IO上存在瓶颈,但是,您可以通过并行化部分查询来获得更快的速度:

file
    //ReadLines is non-greedy equiv of ReadAllLines
    //best to do this on a single thread...
    .SelectMany(i => File.ReadLines(i))
    //now go parallel.
    .AsParallel()
    .SelectMany(line => line.Split(new[] { ' ', ',', '.', '?', '!', },
                        StringSplitOptions.RemoveEmptyEntries))                   
    .GroupBy(word => word)
    .ToDictionary(g => g.Key, g => g.Count());

答案 1 :(得分:0)

你可以试试这些:

  1. 正如Dusan建议的那样,将其转换为标准算法,这样您就可以计算算法的不同部分,看看哪个部分需要更多时间。

  2. 将处理移至后台线程而不是UI线程。这将使您的UI保持响应。

  3. 尝试使用Parallel.For / Parallel.ForEach或Select.AsParallel(Plinq)并行执行操作。请记住线程安全。此外,当您并行执行此操作时,CPU核心数和磁盘吞吐量也很重要。

  4. 查看Regex是否有助于代替手动字符串操作。