[英]RegEx for extracting lines between 2 strings in C#
我在日志文件中有以下數據,我想提取“ Process Started”和“ Process Completed”兩個短語之間的行,包括行的開頭和行的結尾。
2016-11-28 12:18:59.5286 | 14 | Info | Process Started -ABC *****
....
..
2016-11-28 12:18:59.5286 | 14 | Info | Process Completed -ABC, Status: Failed***
2016-11-28 13:18:59.5286 | 14 | Info | Process Started -DEF
....
..
2016-11-28 13:18:59.5286 | 14 | Info | Process Completed -DEF Status: Passed***
使用下面的RegEx,我可以提取行,但是缺少具有給定匹配項的行的開頭和結尾。
Regex r = new Regex("^*?Process Started -"+process.Name+"(.*?)Process Completed: "+process.Name+".*?", RegexOptions.Singleline);
正則表達式上方這樣返回
Process Started -ABC *****
....
..
2016-11-28 12:18:59.5286 | 14 | Info | Process Completed
但是我需要這樣
2016-11-28 12:18:59.5286 | 14 | Info | Process Started -ABC *****
....
..
2016-11-28 12:18:59.5286 | 14 | Info | Process Completed -ABC, Status: Failed***
您接近了,但是最后的懶惰量詞是問題所在:它將與它必須達到的最低要求匹配,在這種情況下,它什么都沒有。
這是有效的正則表達式的修訂:
Regex r = new Regex("[^\n]*?Process Started -"
+ process.Name + "(.*?)Process Completed -"
+ process.Name + "[^\n]*", RegexOptions.Singleline);
我所做的更改:
[^\\n]*
阻止匹配換行符,但獲得其余的行 額外信息:
我不確定您打算如何在代碼的上下文中使用它,但是如果您需要提取所有這些部分,而不是提取一個特定的進程名,則可以使用此變體一次抓住它們:
Regex r = new Regex("[^\n]*?Process Started -(\w+)(.*?)Process Completed -\1[^\n]*", RegexOptions.Singleline);
\\1
是對(\\w+)
匹配的任何進程名稱的反向引用。 您將最終獲得一組匹配項,每個進程名稱一個。
您需要使用“ Multiline
選項,然后可以執行以下操作:
var reg = new Regex(@"^.*Process Started -ABC(.*)$(\n^.*$)*?\n(^.*Process Completed -ABC.*)$",
RegexOptions.Multiline);
但這有點丑陋。 正如@ blaze_125在評論中建議的那樣,最好的辦法是將其分成幾行,然后迭代查找Started
和Completed
字符串,然后抓住它們之間的所有行
您可以執行以下操作:
var lines = str.Split('\n');
var q = new Queue<string>();
foreach (var l in lines)
{
q.Enqueue(l);
if (l.Contains("Process Completed")) // you could use a regex here if you want more
// complex matching
{
string output;
while (q.Count > 0)
{
// your queue here would contain exactly one entry
output = q.Dequeue();
Console.WriteLine(output);
}
}
}
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.