假设我有一个字符串类型
(价格+折扣价格)* 2-最高价格
以及包含每个元素要替换内容的字典
价格:A1折扣价:A2最大价格:A3
我该如何准确地替换每个短语,而又不碰其他短语。搜索Price
的含义不应修改Price
中的Discounted_Price
。结果应该是(A1+A2)*2-A3
而不是(A1+Discounted_A1) - Max.A1
或其他
谢谢。
最佳答案
如果变量可以由字母数字/下划线/点字符组成,则可以将它们与[\w.]+
正则表达式模式匹配,并添加包含.
的边界:
using System;
using System.Collections.Generic;
using System.Text.RegularExpressions;
public class Test
{
public static void Main()
{
var s = "(Price+Discounted_Price)*2-Max.Price";
var dct = new Dictionary<string, string>();
dct.Add("Price", "A1");
dct.Add("Discounted_Price", "A2");
dct.Add("Max.Price","A3");
var res = Regex.Replace(s, @"(?<![\w.])[\w.]+(?![\w.])", // Find all matches with the regex inside s
x => dct.ContainsKey(x.Value) ? // Does the dictionary contain the key that equals the matched text?
dct[x.Value] : // Use the value for the key if it is present to replace current match
x.Value); // Otherwise, insert the match found back into the result
Console.WriteLine(res);
}
}
请参见IDEONE demo
如果匹配项前面带有单词或点字符,则
(?<![\w.])
否定后向匹配项将使匹配失败;如果匹配项之后是单词或点字符,则(?![\w.])
否定的lookahead将使匹配项失败。请注意,
[\w.]+
允许在前导和尾随点处加点,因此,您可能希望将其替换为\w+(?:\.\w+)*
并用作@"(?<![\w.])\w+(?:\.\w+)*(?![\w.])"
。更新
由于您已经提取了要替换为列表的关键字,因此需要使用更复杂的单词边界(不包括点):
var listAbove = new List<string> { "Price", "Discounted_Price", "Max.Price" };
var result = s;
foreach (string phrase in listAbove)
{
result = Regex.Replace(result, @"\b(?<![\w.])" + Regex.Escape(phrase) + @"\b(?![\w.])", dct[phrase]);
}
请参见IDEONE demo。
关于c# - 具有特定单词边界的正则表达式,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/37468103/