逐行读取大文本文件并搜索字符串

我目前正在开发一个应用程序,它读取大约50000行的文本文件。 对于每一行,我需要检查它是否包含特定的字符串。

目前,我使用传统的System.IO.StreamReader逐行读取我的文件。

问题是文本文件的大小每次都会改变。 我做了几个测试性能,我注意到当文件大小增加时,读取一行所需的时间就越多。

例如 :

读取包含5000行的txt文件:0:40
读取包含10000行的txt文件:2:54

读取2倍大的文件需要4倍的时间。 我无法想象读取100000行文件需要多长时间。

这是我的代码:

 using (StreamReader streamReader = new StreamReader(this.MyPath)) { while (streamReader.Peek() > 0) { string line = streamReader.ReadLine(); if (line.Contains(Resources.Constants.SpecificString) { // Do some action with the string. } } } 

有没有办法避免这种情况:更大的文件=更多时间阅读一行?

试试这个:

 var toSearch = Resources.Constants.SpecificString; foreach (var str in File.ReadLines(MyPath).Where(s => s.Contains(toSearch))) { // Do some action with the string } 

这样可以避免在循环之前通过缓存值来访问每次迭代的资源。 如果这没有帮助,请尝试基于高级字符串搜索算法(例如KMP)编写自己的Contains


注意:请务必使用File.ReadLines ,它会懒惰地读取行(与同时查找一次读取所有行的File.ReadAllLines不同)。

使用RegEx.IsMatch ,您应该会看到一些性能改进。

 using (StreamReader streamReader = new StreamReader(this.MyPath)) { var regEx = new RegEx(MyPattern, RegexOptions.Compiled); while (streamReader.Peek() > 0) { string line = streamReader.ReadLine(); if (regEx.IsMatch(line)) { // Do some action with the string. } } } 

但请记住使用已编译的RegEx。 这是一篇非常好的文章 ,你可以看一些基准。

快乐的编码!