我得到内存异常"System.IO.无一例外;错误

本文关键字:System IO 无一例外 错误 quot 内存 异常 | 更新日期: 2023-09-27 18:07:23

对于小目录大小的代码工作正常,当目录文件大小较大时给出此错误信息。

我的代码:
IEnumerable<string> textLines = 
          Directory.GetFiles(@"C:'Users'karansha'Desktop'watson_query'", "*.*")
                   .Select(filePath => File.ReadAllLines(filePath))
                   .SelectMany(line => line)
                   .Where(line => !line.Contains("appGUID: null"))
                   .ToList();
List<string> users = new List<string>();
textLines.ToList().ForEach(textLine =>
{
    Regex regex = new Regex(@"User:'s*(?<username>[^'s]+)");
    MatchCollection matches = regex.Matches(textLine);
    foreach (Match match in matches)
    {
        var user = match.Groups["username"].Value;
        if (!users.Contains(user)) 
            users.Add(user);
    }
});
int numberOfUsers = users.Count(name => name.Length <= 10);
Console.WriteLine("Unique_Users_Express=" + numberOfUsers);

我得到内存异常"System.IO.无一例外;错误

我会使用Directory.EnumerateFilesFile.ReadLines,因为它们较少占用内存,它们像StreamReader一样工作,而Directory.GetFilesFile.ReadAllLines首先读取所有内存:

var matchingLines = Directory.EnumerateFiles(@"C:'Users'karansha'Desktop'watson_query'", "*.*")
    .SelectMany(fn => File.ReadLines(fn))
    .Where(l => l.IndexOf("appGUID: null", StringComparison.InvariantCultureIgnoreCase) >= 0);
foreach (var line in matchingLines)
{
    Regex regex = new Regex(@"User:'s*(?<username>[^'s]+)");
    // etc pp ...
}

您也不需要再次为所有行创建List<string>。只需用foreach枚举查询(textLines.ToList创建第三个集合,也是冗余的)。

尝试使用下一个代码,它使用ReadLines,它不会将整个文件加载到内存中,而是逐行读取文件。它还使用HashSet来存储匹配正则表达式的唯一结果。

Regex regex = new Regex(@"User:'s*(?<username>[^'s]+)");
IEnumerable<string> textLines = 
      Directory.GetFiles(@"C:'Users'karansha'Desktop'watson_query'", "*.*")
               .Select(filePath => File.ReadLines(filePath))
               .SelectMany(line => line)
               .Where(line => !line.Contains("appGUID: null"));
HashSet<string> users = new HashSet<string>(
    textLines.SelectMany(line => regex.Matches(line).Cast<Match>())
             .Select(match => match.Groups["username"].Value)
);
int numberOfUsers = users.Count(name => name.Length <= 10);
Console.WriteLine("Unique_Users_Express=" + numberOfUsers);