我正在尝试创建一个以“WORD”开头的模式,并匹配除原始“WORD”之外的所有字母、数字和字符,直到到达“ENDWORD”为止。
在这个例子中,我希望它匹配第二次出现的“WORD”并匹配直到“ENDWORD”;但是,它从第一次出现开始,并没有正确排除第二次出现的“WORD”。
看起来这个技巧可以匹配除“WORD”之外的任何字符。下面的示例使用由前面的“.”否定的否定前瞻。 (任何),但我不确定如何将肯定的“任何”或换行符集与否定词组合起来。任何帮助将不胜感激。
这是我在 LinqPad 中运行的示例 C# 程序。
无效主函数() {
var text =
@"WORD
[asdf] ---
123/\*&
WORD
[asdf] ---
123/\*&
ENDWORD
[asdf] ---
123/\*&";
var pattern = $"(WORD).|\\n\\b(?!WORD)\\b.|\\n*(ENDWORD)";
Regex rgx = new Regex(pattern);
foreach (Match match in rgx.Matches(text))
{
match.Dump();
}
}
说明问题的另一种方法是从“ENDWORD”(捕获它)开始,回溯,忽略所有字符,直到找到第一次出现的“WORD”并捕获它。只是修改以澄清“ENDWORD”不是字符串的结尾。
最佳答案
对于示例数据,您可以首先匹配前面带有空格或制表符的 WORD
。然后重复匹配不包含 WORD 的行,直到遇到包含 ENDWORD
且前面有空格或制表符的行。
要检查该行是否不包含 WORD,您可以使用否定前瞻。
[ \t]WORD\b.*(?:\r?\n(?!.*[ \t](?:END)?WORD\b).*)*\r?\n[ \t]+ENDWORD\b
说明
[\t]
匹配空格或制表符WORD\b
匹配 WORD 和单词边界.*
匹配除换行符之外的任意字符 0 次以上(?:
非捕获组\r?\n(?!.*[\t](?:END)?WORD\b)
对于不包含可选 END 后接 WORD 的行,重复 0 次以上/里>.*
如果是这种情况,则匹配整行
)*
关闭非捕获组并重复 0 次以上\r?\n[\t]+ENDWORD\b
将换行符、1 个以上空格或制表符以及 ENDWORD 与字边界匹配
例如:
var pattern = @"[ \t]WORD\b.*(?:\r?\n(?!.*[ \t](?:END)?WORD\b).*)*\r?\n[ \t]+ENDWORD\b";
关于c# - 需要一个包含除排除单词之外的任何字符的 C# 正则表达式模式,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/57416386/