C#Regex替换模板内容

时间:2018-03-29 12:54:03

标签: c# regex replace

使用Regex在模板中用值替换关键字时,我测试了以下代码。

string input = "Welcome {{friend}} Get my new {{id}} with {{anonymous}} People";
            Dictionary<string, string> mydict = new Dictionary<string, string> ();
            mydict.Add("friend", "<<My Friend>>");
            mydict.Add("id", "<<Your ID>>");
            string pattern = @"(?<=\{{2})[^}}]*(?=\}{2})";// @"\{{2}^(.*?)$\}{2}";//"^[{{\\w}}]$";
            //var m = Regex.Match(input, @"\{{(.*)\}}");
            string regex = Regex.Replace(input, pattern, delegate(Match match) {
                string v = match.ToString();
                return mydict.ContainsKey(v) ? mydict[v] : v;

            });

            Console.WriteLine(regex);

curley braces仍然保留在输出中,这是不希望的

我需要<<My Friend>>而不是{{ <<My Friend>> }}。 我很感激你的建议。

2 个答案:

答案 0 :(得分:1)

大括号保留在原始文本中,因为您使用的是零宽度前瞻和后置构造。这使得内容与正则表达式的捕获值之外的(?<=...)(?=...)匹配,因此不会被替换。

要解决此问题,请从正则表达式中删除前瞻和后瞻,在标记文本周围放置一个捕获组,并使用它来搜索替换字典:

string pattern = @"\{{2}([^}}]*)\}{2}";
...
var v = match.Group[1].Value;
return mydict.ContainsKey(v) ? mydict[v] : v;

答案 1 :(得分:0)

您可以使用简单的{{(.*?)}}正则表达式并使用Group 1 vlaue来检查词典匹配:

string pattern = @"{{(.*?)}}";
string regex = Regex.Replace(input, pattern, delegate(Match match) {
     string v = match.Groups[1].Value;
     return mydict.ContainsKey(v) ? mydict[v] : v;
});
// => Welcome <<My Friend>> Get my new <<Your ID>> with anonymous People

与lambda表达式相同的代码:

string regex = Regex.Replace(input, pattern, x =>
     mydict.ContainsKey(match.Groups[1].Value) ?
                mydict[match.Groups[1].Value] : match.Groups[1].Value;
});

请参阅C# demo

请注意,[^}}]并不意味着匹配}} 以外的任何文字,它只匹配}以外的任何字符,与{{1}相同},所以[^}]在这种情况下更可取。如果您在.*?\w+之间只有字母,数字和下划线,则甚至可以{{