我正在尝试捕获由另一个关键字或行尾划分的关键字的值,关键字可能以任何顺序重复,或者没有要捕获的数据:
关键词: K1,K2
输入数据: somedatahereornotk1capturethis1k2capturethis2k2capturethis3k1k2
我希望捕获的数据是
1. capturethis1
2. capturethis2
3. capturethis3
4.
5.
我已尝试k1|k2(?<Data>.*?)k1|k2
,但捕获的数据始终为空。
谢谢!
答案 0 :(得分:3)
您正处于改变的正确轨道上。缺少的部分是使用look-behind和look-ahead断言必须在分隔符之前和之后的某些内容。
(?<=k1|k2)(?<Data>.*?)(?=k1|k2)
Lookbehind (?<=…)
和lookahead (?=…)
是零宽度断言,因此必须满足它们但不会成为匹配的一部分。
你想要捕获连续分界符的实例有点棘手,因为你无法真正捕获“无” - 两个字符之间的空间。一种方法是捕捉后视(或前瞻):
(?<=(?<Delimiter>k1|k2))(?<Data>.*?)(?=k1|k2)
这将产生4个结果而不是3个结果,因为它将在样本数据的末尾包含连续的k1k2
。您只需忽略每次匹配的额外数据(k1
,k2
,k2
,k1
)。
答案 1 :(得分:3)
首先,请注意,交替运算符|
的优先级较低,因此
k1|k2(?<Data>.*?)k1|k2
实际上是在寻找k1
或k2(?<Data>.*?)k1
或k2
。使用分组:
(?:k1|k2)(?<Data>.*?)(?:k1|k2)
其次,考虑使用零宽度前瞻和后观断言:
(?<=k1|k2)(?<Data>.*?)(?=k1|k2)
答案 2 :(得分:0)
string s="somedatahereornotk1capturethis1k2capturethis2k2capturethis3k1k2";
Regex r=new Regex("(?<=k1|k2).*?(?=k1|k2)");
foreach(Match m in r.Matches(s))
Console.WriteLine(m.Value);