我有一个string Snippet
和一个IEnumerable<string> Highlights
。我想在Snippet
中搜索Highlights
中任何字符串的所有实例,然后用跨度将单词包装起来。当只有一个Regex.Replace
时,我已经设置了一个string Highlight
,但是现在有很多选项,我不确定如何更改代码。
例:
Snippet = "Jack and Jill went up the hill to fetch some water"
Highlights = "Jack", "hill", "to"
预期结果:
Snippet = "<span>Jack</span> and Jill went up the <span>hill</span> <span>to</span> fetch some water"
单个字符串的旧代码:
Regex.Replace(Snippet, Highlight, ReplaceHighlightWords, RegexOptions.IgnoreCase
private string ReplaceHighlightWords(Match m)
{
return "<span class=\"text-highlight\">" + m.Value + "</span>";
}
最佳答案
您可以使用交替:
var rx = string.Forma(@"\b(?:{0})\b", string.Join("|", Highlights));
var res = Regex.Replace(Snippet, rx,
"<span class=\"text-highlight\">$&</span>",
RegexOptions.IgnoreCase);
当您在
\b
中同时具有to
和together
时,边界Highlights
一词将处理这些情况。注意,您可以完全省略\b
来匹配单词中的子字符串。替换模式中的
$&
将整个匹配值插入结果中。如果
Highlights
可能包含特殊字符,例如(
或[
,请先使用Regex.Escape
对其进行转义,并且-如果仅在这种情况下要匹配整个单词,请使用\b
代替@"(?<!\w)(?:{0})(?!\w)"
。这是更高级的代码段:var Snippet = "Jack and Jill went up the (hill) to fetch some water";
var Highlights = new string[] { "Jack", "(hill)", "to" };
var rx = string.Format(@"(?<!\w)(?:{0})(?!\w)",
string.Join("|", Highlights.Select(p => Regex.Escape(p))));
var res = Regex.Replace(Snippet, rx,
"<span class=\"text-highlight\">$&</span>",
RegexOptions.IgnoreCase);
Console.WriteLine(res);
// => <span class="text-highlight">Jack</span> and Jill went up the
// <span class="text-highlight">(hill)</span> <span class="text-highlight">to</span>
//fetch some water
见this IDEONE demo
关于如何为基于正则表达式的替换构建优化的替代列表的线程,如Generating the Shortest Regex Dynamically from a source List of Strings所示,也可能值得检查。
关于c# - C#用IEnumerable <string>中的任何字符串替换字符串中的所有实例,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/37977328/