【问题标题】:Regular Expression to ignore empty href忽略空href的正则表达式
【发布时间】:2014-03-11 18:45:10
【问题描述】:

我写了一个函数来替换 href 的值与 somevalue + 原始 href

说:-

<a href="/somepage.htm" id="test">

替换为

<a href="http//www.stackoverflow.com/somepage.htm" id="test">

不需要更换的地方:-

<a href="http//www.stackoverflow.com/somepage.htm" id="test">
 <a href="#" id="test">
<a href="javascript:alert('test');" id="test">
<a href="" id="test">

我编写了以下方法,适用于所有情况,但不适用于 href 的空白值

public static string RelativeToAbsoluteURLS(string text, string absoluteUrl, string pattern = "src|href")
    {
        if (String.IsNullOrEmpty(text))
        {
            return text;
        }
        String value = Regex.Replace(text, "<(.*?)(" + pattern + ")=\"(?!http|javascript|#)(.*?)\"(.*?)>", "<$1$2=\"" + absoluteUrl + "$3\"$4>", RegexOptions.IgnoreCase | RegexOptions.Multiline);

        return value.Replace(absoluteUrl + "/", absoluteUrl);
    }

?!http|javascript|# 忽略http, javascript, #,所以它适用于这些情况,但如果我们考虑以下部分

(?!http|javascript|#)(.*?)

并将此 * 替换为 +

(?!http|javascript|#)(.+?)

它不适用于空箱。

【问题讨论】:

  • 问题足够大,我需要它来处理&lt;a href="" id="test"&gt; case
  • 感谢您的评论,我已经编写了一个单独的HTML解析类,该方法是实用程序类的一部分,它具有针对某些特殊场景的某些方法,该函数就是其中之一。跨度>
  • 这里我不希望这种方法适用于标签,唯一的期望是它应该适用于"" 而且我也不希望它适用于所有情况[作为正则表达式不是最好的方法],至少对于我想要的人来说

标签: c# html regex


【解决方案1】:

* 更改为+ 不起作用,因为你完全弄错了:

  • * 表示“零个或多个”
  • + 表示“一个或多个”

因此,使用+,您是在强制内容出现在该位置,而不是让内容丢失。

您弄错的另一件事是展示位置。那个地方的* 指的是.。它们一起表示“零个或多个字符”。所以,这部分已经不需要任何内容了。因此,由于您的正则表达式目前不适用于空内容,因此 other 似乎需要这样做。

看前面的表达式:

(?!http|javascript|#)(.*?)

?! 是一个零宽度的负前瞻。零宽度。消极的。这意味着它也不需要任何内容​​。

所以,我得到了你的代码,将它粘贴到 the online compiler,然后我用你的示例输入它 &lt;a href="" id="test"&gt;

使用 System.IO; 使用系统; 使用 System.Text.RegularExpressions;

class Program
{
    static void Main()
    {
        string text = "<a href=\"\" id=\"test\">";
        string pattern = "src|href";
        string absoluteUrl = "YADA";
        string value = Regex.Replace(text, "<(.*?)(" + pattern + ")=\"(?!http|javascript|#)(.*?)\"(.*?)>", "<$1$2=\"" + absoluteUrl + "$3\"$4>", RegexOptions.IgnoreCase | RegexOptions.Multiline);

        Console.WriteLine(value);
    }
}

猜猜它的作用:

Compiling the source code....
$mcs main.cs -out:demo.exe 2>&1

Executing the program....
$mono demo.exe 
<a href="YADA" id="test">

所以,要么您没有说实话,要么您在此处发布代码时更改了代码,或者您的代码中有其他完全混乱的东西,对不起。

编辑:

所以,原来 href="" 是要被忽略的。

然后,您可以做的最简单的事情是添加另一个否定前瞻,这将明确阻止 href="" 案例。但是,请注意,该组的位置会有所不同。当前组位于 href 的引号内,因此它无法“窥视”整个 href 引号的外观。新组必须在引号之前。

"<(.*?)(" + pattern + ")=(?!\"\")\"(?!http|javascript|#)(.*?)\"(.*?)>"

请注意,就在 href 的第一个引用之前,我添加了一个 (?!\"\"),以确保“不会出现引用跟随引用的情况”。

【讨论】:

  • 你解释的很好,但是我不想换成雅达,应该是这样,javascript#是这样的,所以不应该换成雅达
  • @vikas:等等,所以你想让href=""被解析器命中?
  • 但其他情况正在丢失,正在失去原始价值
【解决方案2】:

我知道你要的是 RegEx。

但这里有一个替代方案,因为我认为使用Uri.IsWellFormedUriString 是值得的。 这样你也可以重用辅助函数:

public string RelativeToAbsoluteURLS(string text, string absoluteUrl, string pattern = "src|href")
{
    if (isHrefRelativeURIPath(text)){
        text = absoluteUrl + "/" + System.Text.RegularExpressions.Regex.Replace("///days/hours.htm", @"^\/+", "");
    }

    return text;
}

public bool isHrefRelativeURIPath(string value) {
    if (isLink(value) ||
        value.StartsWith("#") ||
        value.StartsWith("javascript"))
    {
        return false;
    }

    // Others Custom exclusions

    return true;
}


public bool isLink(string value) {
    if (String.IsNullOrEmpty(value))
        return false;

    return Uri.IsWellFormedUriString("http://" + value, UriKind.Absolute);
}

【讨论】:

  • 感谢@Andre,但这仅适用于只有 uri 而不是带有 html 内容的字符串的情况,例如 href="someexample.com" :(
猜你喜欢
  • 2021-09-13
  • 2020-08-06
  • 2011-08-12
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2016-03-30
相关资源
最近更新 更多