我有一个不超过10KB的日志文件(文件大小最多可达2 MB),我想查找文件中是否至少出现一组这些字符串。这些字符串将在不同的行上,如
ACTION:.......
INPUT:...........
结果:..........
如果文件中存在上述一组,我至少需要知道。我已经做了大约100次测试(每次日志不同,所以我重新加载并阅读日志),所以我正在寻找最快和下注的方式来做到这一点。
我在论坛中查找找到最快的方法,但我认为我的文件对于那些问题来说太大了。
Thansk寻找。
答案 0 :(得分:5)
我会逐行阅读并检查条件。一旦你看到一个组,你就可以退出。这样您就不需要将整个文件读入内存。像这样:
public bool ContainsGroup(string file)
{
using (var reader = new StreamReader(file))
{
var hasAction = false;
var hasInput = false;
var hasResult = false;
while (!reader.EndOfStream)
{
var line = reader.ReadLine();
if (!hasAction)
{
if (line.StartsWith("ACTION:"))
hasAction = true;
}
else if (!hasInput)
{
if (line.StartsWith("INPUT:"))
hasInput = true;
}
else if (!hasResult)
{
if (line.StartsWith("RESULT:"))
hasResult = true;
}
if (hasAction && hasInput && hasResult)
return true;
}
return false;
}
}
此代码检查是否有以ACTION开头的行,然后是INPUT,然后是RESULT。如果这些顺序不重要,那么您可以省略if () else if ()
检查。如果该行未以字符串开头,请将StartsWith
替换为Contains
。
答案 1 :(得分:3)
这是一种可行的方法:
StreamReader sr;
string fileContents;
string[] logFiles = Directory.GetFiles(@"C:\Logs");
foreach (string file in logFiles)
{
using (StreamReader sr = new StreamReader(file))
{
fileContents = sr.ReadAllText();
if (fileContents.Contains("ACTION:") || fileContents.Contains("INPUT:") || fileContents.Contains("RESULT:"))
{
// Do what you need to here
}
}
}
您可能需要根据您的确切实施需求做一些变化 - 例如,如果单词跨越两行,该行是否需要以单词开头等等。
<强>加强>
替代逐行检查:
StreamReader sr;
string[] lines;
string[] logFiles = Directory.GetFiles(@"C:\Logs");
foreach (string file in logFiles)
{
using (StreamReader sr = new StreamReader(file)
{
lines = sr.ReadAllLines();
foreach (string line in lines)
{
if (line.Contains("ACTION:") || line.Contains("INPUT:") || line.Contains("RESULT:"))
{
// Do what you need to here
}
}
}
}
答案 2 :(得分:2)
看看How to Read Text From a File。您可能还想查看String.Contains()方法。
基本上你会循环遍历所有文件。对于逐行读取的每个文件,并查看是否有任何行包含1个特殊的“章节”。
答案 3 :(得分:2)
在效率方面,您没有太多关于文本文件的选择。最简单的方法肯定是遍历每一行数据。当您在字符串中抓取一行时,将其拆分为空格。然后将这些单词与您的单词匹配,直到找到匹配项。然后做你需要的任何事情。
我不知道如何在c#中执行此操作,但在vb中它将类似于......
Dim yourString as string
Dim words as string()
Do While objReader.Peek() <> -1
yourString = objReader.ReadLine()
words = yourString.split(" ")
For Each word in words()
If Myword = word Then
do stuff
End If
Next
Loop
希望有所帮助
答案 4 :(得分:0)
此代码示例在大文本文件中搜索字符串。单词包含在HashSet中。它将找到的行写到临时文件中。
if (File.Exists(@"temp.txt")) File.Delete(@"temp.txt");
String line;
String oldLine = "";
using (var fs = File.OpenRead(largeFileName))
using (var sr = new StreamReader(fs, Encoding.UTF8, true))
{
HashSet<String> hash = new HashSet<String>();
hash.Add("house");
using (var sw = new StreamWriter(@"temp.txt"))
{
while ((line = sr.ReadLine()) != null)
{
foreach (String str in hash)
{
if (oldLine.Contains(str))
{
sw.WriteLine(oldLine);
// write the next line as well (optional)
sw.WriteLine(line + "\r\n");
}
}
oldLine = line;
}
}
}