使用StreamReader跳过行

时间:2018-09-07 15:15:32

标签: c# .net-core

我有一个很大的文件,大约有30.000行。我必须解析此文件,并且不能删除该文件上的条目。所以我的想法是跳过所有现成的阅读行。我尝试过这样的事情:

                //Gets the allready readed lines
                int readLines = GetCurrentCounter();
                //Open File
                FileStream stream = new FileStream(LogDatabasePath, FileMode.Open, FileAccess.Read, FileShare.ReadWrite);
                using (StreamReader reader = new StreamReader(stream))
                {
                    int counter = 0;
                    string line;
                    //If File was allready read to a specified line, skip these lines
                    if (readLines != 0) reader.ReadLine().Skip(readLines);
                    //Check if new lines are available
                    while ((line = reader.ReadLine()) != null)
                    {
                        if (counter >= readedLines)
                        {
                            //If there is text which contains the searched Testsystem-Name
                            if (line.Contains(TestSystemName.ToUpper()))
                            {
                                //Create new Database-Entry
                                new TestsystemError().GenerateNewDatabaseEntry(line, counter);
                            }
                        }
                        System.Console.WriteLine(line);
                        counter++;
                    }

                }

问题是,函数reader.ReadLine()。Skip(readLines)没有功能,或者我以错误的方式使用它。

我需要不使用函数“ reader.ReadLine()”而跳过行,因为这非常慢(如果我必须遍历约30.000行的所有行,则会遇到性能问题)。

是否可以跳过行?如果是这样,那将是共享代码的好方法。谢谢。

3 个答案:

答案 0 :(得分:3)

方法reader.ReadLine()返回一个字符串。

扩展方法Skip(readedLines)对该字符串进行迭代,并返回一个迭代器,该迭代器已跳过该字符串中的前readedLines个字符。

这对读者没有影响。

如果您要跳过前 n 行,请通过调用reader.ReadLine() n 次来读取前 n 行,或读取流,直到您在创建阅读器之前阅读了 n 行尾字符序列。后一种方法避免为您要忽略的行创建字符串,而是更多代码。

如果您碰巧具有非常规则的数据,因此所有行的长度都相同,那么您可以在创建阅读器之前跳过流

FileStream stream = new FileStream(LogDatabasePath, FileMode.Open, FileAccess.Read, FileShare.ReadWrite);

stream.Seek(readedRows * lengthOfRowInBytes, SeekOrigin.Begin);

using (StreamReader reader = new StreamReader(stream))
  // etc

如果您在行中编码了行号,则还可以执行二进制搜索,但这是更多的代码。

答案 1 :(得分:2)

代替跟踪行数,而是跟踪读取的字符数。然后,您可以使用stream.Seek()快速跳到最后一个读取位置,而不必每次都遍历整个文件。

long currentPosition = GetCurrentPosition();

//Open File
FileStream stream = new FileStream(LogDatabasePath, FileMode.Open, FileAccess.Read, FileShare.ReadWrite);
using (StreamReader reader = new StreamReader(stream))
{
    string line;

    // Seek to the previously read position
    stream.Seek(currentPosition, SeekOrigin.Begin);

    //Check if new lines are available
    while ((line = reader.ReadLine()) != null)
    {
        // do stuff with the line
        // ...
        Console.WriteLine(line);

        // keep track of the current character position
        currentPosition += line.Length + 2; // Add 2 for newline
    }
}

SaveCurrentPosition(currentPosition);

答案 2 :(得分:0)

您应在阅读时跳过这些行

//If File was allready read to a specified line, skip these lines
while ((line = reader.ReadLine()) != null && readLines < readedLines){
   readLines++
} 
if (readedLines != 0) reader.ReadLine()
//Check if new lines are available
while ((line = reader.ReadLine()) != null)