所以基本上,我的輸入字串是某種包含我想要匹配的關鍵字的文本,前提是:
- 每個關鍵字可能有空格/非單詞字符前/附加,或沒有
(|\s\W) - 必須有一個非單詞/空白字符分隔多個關鍵字,或者關鍵字位于行首/行尾
- 僅作為子字串出現的關鍵字不計算在內,例如
bar不匹配foobarbaz
例如:
input: "#foo barbazboo tree car"
keywords: {"foo", "bar", "baz", "boo", "tree", "car"}
我正在使用可列舉的關鍵字和字串生成器在 C# 中動態生成正則運算式
StringBuilder sb = new();
foreach (var kwd in keywords)
{
sb.Append($"((|[\\s\\W]){kwd}([\\s\\W]|))|");
}
sb.Remove(sb.Length - 1, 1); // last '|'
_regex = new Regex(sb.ToString(), RegexOptions.Compiled | RegexOptions.IgnoreCase);
在regexr.com上測驗此模式,給定輸入匹配所有關鍵字。但是,我不想{bar, baz, boo}包含在內,因為每個關鍵字之間沒有空格。理想情況下,我希望我的正則運算式只匹配{foo, tree, car}.
修改我的模式 like(( |[\s\W])kwd([\s\W]| ))會導致{bar, baz, boo}不包括在內,但會產生虛假 on {tree, car},因為在這種情況下,關鍵字之間必須至少有兩個空格。
如何指定“可能只有一個空格分隔兩個關鍵字”,或者換句話說,“半個空格就可以”,保留動態創建正則運算式的能力?
uj5u.com熱心網友回復:
在您的情況下,您需要構建
var pattern = $@"\b(?:{string.Join("|", keywords.OrderByDescending(x => x.Length).Select(Regex.Escape))})\b";
_regex = new Regex(pattern, RegexOptions.Compiled | RegexOptions.IgnoreCase);
在這里,您將在較短的關鍵字之前獲得較長的關鍵字,因此,如果您有foo,bar和foo bar,則該模式將看起來像\b(?:foo\ bar|foo|bar)\band 將匹配foo bar,而不是fooandbar一旦有這樣的匹配。
如果您的關鍵字看起來像keywords: {"$foo", "^bar^", "[baz]", "(boo)", "tree ", " car"},即它們可以在關鍵字的開頭/結尾有特殊字符,您可以使用
_regex = new Regex($@"(?!\B\w)(?:{string.Join("|", keywords.Select(Regex.Escape))})(?<!\w\B)", RegexOptions.Compiled | RegexOptions.IgnoreCase);
這$@"(?!\B\w)(?:{string.Join("|", keywords.OrderByDescending(x => x.Length).Select(Regex.Escape))})(?<!\w\B)"是一個插入的逐字字串文字,包含
(?!\B\w)- 左手自適應動態詞邊界(?:- 非捕獲組的開始:{string.Join("|", keywords.OrderByDescending(x => x.Length).Select(Regex.Escape))}- 按長度降序對關鍵字進行排序,將它們轉義并加入|
)- 小組結束(?<!\w\B)- 右手自適應動態詞邊界。
轉載請註明出處,本文鏈接:https://www.uj5u.com/houduan/429093.html
上一篇:正則運算式屬性標題大小寫(Lt)
