我有一个非常简单的 reg ex 问题。我的 HTML 标记如下所示:
<body lang=EN-US link=blue vlink=purple>
我想清除所有属性并返回<body>
还有许多其他 HTML 标记我想清除其属性,因此我希望重用该解决方案。如何用正则表达式做到这一点?谢谢,B。
像这样使用HtmlAgilityPack:
public string RemoveAllAttributesFromEveryNode(string html)
{
var htmlDocument = new HtmlAgilityPack.HtmlDocument();
htmlDocument.LoadHtml(html);
foreach (var eachNode in htmlDocument.DocumentNode.SelectNodes("//*"))
eachNode.Attributes.RemoveAll();
html = htmlDocument.DocumentNode.OuterHtml;
return html;
}
调用此方法,传递要从中删除所有属性的 html。
xpath将在这方面为您提供很多帮助。
不要对可能包含脚本的 html 文件使用正则表达式,如在 Javascript 中,字符<
不是>
标记分隔符而是运算符。正则表达式可能会将这些运算符匹配为标签,这将完全弄乱文档。
不要使用正则表达式来解析 HTML - 它不是一个很好的工具。如果您无法控制 HTML 的传入格式,则尤其如此。
为此请使用HTML Agility Pack 。
它是一个 .NET 代码库,允许您解析“网络之外”的 HTML 文件。解析器对“真实世界”格式错误的 HTML 非常宽容。对象模型与 System.Xml 的提议非常相似,但用于 HTML 文档(或流)。
如果您的 HTML 没有被彻底破坏,并且属性不包含>
符号,那么它很简单:
<body.+?>
...如果您想防止 XSS 或其他东西,请忽略这一点。
如果您的属性可能包含其他符号,那么这是一个完整的示例:
string data = @"<body lang=""EN-US>"" link=blue vlink=purple>";
Regex re = new Regex(@"<(body).*?(""[^""]+""[^"">]+)*>");
Console.WriteLine(re.Replace(data, "<$1>")); // <body>
请注意,HTML 仍然需要格式正确。
一般来说,不建议使用正则表达式来解析 html,但如果你必须使用它,
对于你的问题,类似下面的东西会起作用。
在这个正则表达式中,'body' 与'span' 作为一个例子。另请注意,注释会被忽略,因为它们可能会隐藏 html。出于同样的原因考虑脚本。
我会留下评论部分。您必须知道脚本可以更改文档呈现并使用可以隐藏您可能想要处理的 html 的语言结构。当然,这不应该用正则表达式来完成。
如果您愿意,您可以删除“脚本”子表达式,以期修改包含您想要更改的内容的可能字符串常量。不过不推荐。
原始正则表达式(修饰符:扩展,“点包括换行符”)
在 C# 中,可以命名正则表达式捕获的缓冲区,以便每个 OR 的子表达式包含相同的名称。示例: (?<begin> ..) .. (?<end> ..) | (?<begin> ..) .. (?<end> ..)
所以替换只是 ["begin"] + ["end"]。这是 Perl 5.10 中的错误,所以我只使用捕获缓冲区编号,Dot Net 可能会正常工作。
搜索
# (1,2)
( <!--.*?--> ) ()
|
# (3,4)
(
(?:
<script
(?>
(?:\s+(?:".*?"|'.*?'|[^>]*?)+)?
\s*
>
)(?<!/> )
.*?
</script\s*>
|
</?script (?:\s+(?:".*?"|'.*?'|[^>]*?)+)? \s*/?>
)
) ()
|
# (5,6)
( <(?:body|span) ) (?!\s*/?>)
\s+ (?:".*?"|'.*?'|[^>]*?)+
( /?> )
代替
$1$2$3$4$5$6
以下正则表达式清除给定字符串中所有 HTML/XML 节点的属性。
\<[a-z]+\b([^>]+?)\s?\/?\>
作为 C# 函数,它看起来像这样:
public string RemoveAttributes(string value){
var attributeClean = new System.Text.RegularExpressions.Regex(@"\<[a-z]+\b([^>]+?)\s?\/?\>", System.Text.RegularExpressions.RegexOptions.Multiline | System.Text.RegularExpressions.RegexOptions.IgnoreCase);
while (attributeClean.IsMatch(value)) {
var match = attributeClean.Match(value);
value = value.Remove(match.Index, match.Length);
}
return value;
}
如果只想清理特定元素,可以使用以下正则表达式
\<(?:li|body)([^>]+?)\s?\/?\>
并将尽可能多的元素添加到由 a 分隔的第一个不匹配组中|
。