【问题标题】:Trouble with Regular Expressions replacing custom tags in C#正则表达式替换 C# 中的自定义标签的问题
【发布时间】:2014-05-29 15:07:50
【问题描述】:

我有一个简单的编辑器,允许人们使用它来更新网站部分的文本。 当我实际呈现它们的内容时,我允许使用 html 替换几个伪标签。我想使用正则表达式来定位这些标签并用适当的 html 标记替换它们。

基本上会有一个文本块,其中可能包含以下一个或多个嵌入的伪标签,我需要使用 c# 通过正则表达式替换这些标签:

[E]me@myemail.com[/E] 

需要变成

<a class='LinkText' href='mailto:me@myemail.com'>me@myemail.com</a>

[L text='My Link Text']www.google.com[/L]

需要变成

<a class="MyLinkClass" href="www.google.com">My Link Text</a>

对于电子邮件伪标签,我想出了以下正则表达式,但它不起作用:

Content = Regex.Replace(Content, @"\[E\](?(email)[^<>]+)\[/E\]", "<a class='LinkText' href='mailto:?{email}'>?{email}</a>");

由于我被困在这一方面,我在另一方面也没有取得太大进展。

有什么想法可以让它发挥作用吗?我一直在为这些正则表达式的语法而苦苦挣扎......任何帮助或指导将不胜感激!

【问题讨论】:

  • 我没有解析 HTML。我正在解析文字 TEXT,其中仅包含这两个伪标签。
  • 你必须只使用正则表达式吗?我会做正则表达式来获取电子邮件。然后我会使用 string.Format 来创建替换文本。然后你可以做一个常规的字符串替换。只是一个替代的想法......

标签: c# html regex replace


【解决方案1】:

几点建议:

  1. 您似乎正在尝试使用named capture groups。您可以使用(?&lt;name&gt;subexpression) 在正则表达式中创建其中之一
  2. 使用Regex.Replace 访问命名捕获组时,您可以使用${name} 访问命名捕获组。

除此之外,您非常接近。这里有两个正则表达式应该是一个很好的起点:

链接:

string linkReplacement = 
    Regex.Replace(
        linkContent, 
        @"\[L text='(?<text>[^']*)'\](?<link>[^\]]*)\[/L\]", 
        "<a class='MyLinkClass' href='${link}'>${text}</a>");

电子邮件:

string emailReplacement = 
    Regex.Replace(
        emailContent, 
        @"\[E\](?<email>[^\]]*)\[/E\]", 
        "<a class='LinkText' href='mailto:${email}'>${email}</a>");

工作示例: https://dotnetfiddle.net/nhsoJ9

编辑:更新以消除贪婪。

【讨论】:

  • 我投了赞成票。我喜欢使用命名的捕获组。我以前没用过那些:)
  • 这就像一个魅力!希望将其保留为单线,这正是我想要实现的目标。感谢您使命名分组的语法更加清晰,我认为这是我最大的绊脚石。
  • 当心贪婪的.*! (即上述模式有一些严重的问题 - 请务必在一行上使用多个标签和跨越多行的标签来测试此解决方案。结果可能令人惊讶。)
  • @ridgerunner:感谢您的免责声明。这只是一个起点,绝不是一个完整的解决方案。
  • @ridgerunner:我已经更新了正则表达式。你介意看看吗?
【解决方案2】:

在 LINQPad 中搞定了这个...

void Main()
{
    string s = 
    @"[E]me@myemail.com[/E]
    blagra
    shlarga";
    foreach ( Match m in Regex.Matches( s, @"\[E\](\w+@\w+.\w+)\[/E\]") )
    {
      string emailMatch = m.Groups[1].Value;
      string entireMatch = m.Groups[0].Value;
      string replacement = string.Format( @"<a class=""MyLinkClass"" href=""{0}"">My Link Text</a>", m.Groups[1] );   
      string newString = s.Replace( entireMatch, replacement );
      newString.Dump();
    }

}

第二个替换留给读者作为练习:) ;-)

你可以简化这条线:

foreach ( Match m in Regex.Matches( s, @"\[E\](\w+@\w+.\w+)\[/E\]") )

成为:

foreach ( Match m in Regex.Matches( s, @"\[E\](.+)\[/E\]") ) 

如果你愿意。

【讨论】:

    猜你喜欢
    • 2020-03-21
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2023-04-02
    • 2018-06-21
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多