如何使用C#正则表达式替换/删除所有HTML标签,包括尖括号?有人可以帮我提供代码吗?
如何使用C#正则表达式替换/删除所有HTML标签,包括尖括号?有人可以帮我提供代码吗?
Answers:
如前所述,您不应使用正则表达式来处理XML或HTML文档。它们在HTML和XML文档中表现不佳,因为无法以一般方式表达嵌套结构。
您可以使用以下内容。
String result = Regex.Replace(htmlDocument, @"<[^>]*>", String.Empty);
这在大多数情况下都可以使用,但是在某些情况下(例如,包含尖括号的CDATA)将无法正常使用。
正确的答案是不要这样做,请使用HTML Agility Pack。
编辑添加:
为了毫不掩饰地从jesse的下面的评论中窃取,并避免被指责在所有这些时间之后都未回答问题,以下是使用HTML Agility Pack的一个简单,可靠的代码段,该代码段甚至可以用于格式最不完整,反复无常的HTML代码:
HtmlDocument doc = new HtmlDocument();
doc.LoadHtml(Properties.Resources.HtmlContents);
var text = doc.DocumentNode.SelectNodes("//body//text()").Select(node => node.InnerText);
StringBuilder output = new StringBuilder();
foreach (string line in text)
{
output.AppendLine(line);
}
string textOnly = HttpUtility.HtmlDecode(output.ToString());
使用正则表达式解析HTML的情况很少,因为没有上下文感知就无法正确解析HTML,即使在非传统的正则表达式引擎中也很难提供上下文感知。您可以使用RegEx到达那里,但是您需要进行手动验证。
Html Agility Pack可以为您提供一个强大的解决方案,它将减少手动修复因天真地将HTML视为上下文无关语法而导致的像差的需求。
正则表达式在大多数情况下可能会为您提供大部分所需的信息,但是在非常常见的情况下它将失败。如果您能找到比HTML Agility Pack更好/更快的解析器,那就去吧,但是请不要让世界遭受更多破碎的HTML骇客攻击。
这个问题太广泛了,无法确切地回答。您是在谈论从真实的HTML文档(例如网页)中删除所有标签吗?如果是这样,您将必须:
那只是我的头上了-我敢肯定还有更多。完成所有这些操作后,您最终将在某些地方同时使用单词,句子和段落,而在其他地方则使用了大量的无用空格。
但是,假设您只使用一个片段,而只需删除所有标签就可以摆脱困境,这是我要使用的正则表达式:
@"(?></?\w+)(?>(?:[^>'""]+|'[^']*'|""[^""]*"")*)>"
用单引号和双引号引起来的字符串进行匹配足以解决属性值中尖括号的问题。我认为不需要显式匹配标记中的属性名称和其他内容,就像Ryan的答案中的regex一样。第一种方法可以处理所有这些问题。
如果您想知道这些(?>...)
构造,它们就是原子团。它们使regex更加有效,但是更重要的是,它们防止了失控的回溯,当您混合交替和嵌套的量词时,您应该始终注意这一点,就像我所做的那样。我真的不认为这会是一个问题,但是我知道,如果我不提的话,其他人也会。;-)
当然,此正则表达式并不完美,但它可能与您需要的一样好。
Regex regex = new Regex(@"</?\w+((\s+\w+(\s*=\s*(?:"".*?""|'.*?'|[^'"">\s]+))?)+\s*|\s*)/?>", RegexOptions.Singleline);
@JasonTrue是正确的,剥离HTML标签不应通过正则表达式完成。
使用HtmlAgilityPack剥离HTML标签非常简单:
public string StripTags(string input) {
var doc = new HtmlDocument();
doc.LoadHtml(input ?? "");
return doc.DocumentNode.InnerText;
}
我想回覆Jason的回应,尽管有时您需要天真地解析一些HTML并提取文本内容。
我需要使用由富文本编辑器创建的一些HTML来做到这一点,并且总是很有趣和很有趣。
在这种情况下,您可能需要删除某些标签的内容以及标签本身。
就我而言,标签被扔进了这个混音中。某些人可能会发现我(很少)天真的实现是一个有用的起点。
/// <summary>
/// Removes all html tags from string and leaves only plain text
/// Removes content of <xml></xml> and <style></style> tags as aim to get text content not markup /meta data.
/// </summary>
/// <param name="input"></param>
/// <returns></returns>
public static string HtmlStrip(this string input)
{
input = Regex.Replace(input, "<style>(.|\n)*?</style>",string.Empty);
input = Regex.Replace(input, @"<xml>(.|\n)*?</xml>", string.Empty); // remove all <xml></xml> tags and anything inbetween.
return Regex.Replace(input, @"<(.|\n)*?>", string.Empty); // remove any tags but not there content "<p>bob<span> johnson</span></p>" becomes "bob johnson"
}
<xml>.*(?!</xml>)</xml>
与RegexOptions.SingleLine
修改前两个和<[^>]*>
最后。也可以通过捕获的第一个标签名称的替换以及在否定的超前标签和最终标签中的反向引用来组合第一个标签。
尝试在此URL上使用正则表达式方法:http : //www.dotnetperls.com/remove-html-tags
/// <summary>
/// Remove HTML from string with Regex.
/// </summary>
public static string StripTagsRegex(string source)
{
return Regex.Replace(source, "<.*?>", string.Empty);
}
/// <summary>
/// Compiled regular expression for performance.
/// </summary>
static Regex _htmlRegex = new Regex("<.*?>", RegexOptions.Compiled);
/// <summary>
/// Remove HTML from string with compiled Regex.
/// </summary>
public static string StripTagsRegexCompiled(string source)
{
return _htmlRegex.Replace(source, string.Empty);
}
使用此方法删除标签:
public string From_To(string text, string from, string to)
{
if (text == null)
return null;
string pattern = @"" + from + ".*?" + to;
Regex rx = new Regex(pattern, RegexOptions.Compiled | RegexOptions.IgnoreCase);
MatchCollection matches = rx.Matches(text);
return matches.Count <= 0 ? text : matches.Cast<Match>().Where(match => !string.IsNullOrEmpty(match.Value)).Aggregate(text, (current, match) => current.Replace(match.Value, ""));
}