删除Regex.Match字符串的部分内容
本文关键字:Regex Match 字符串 删除 | 更新日期: 2023-09-27 17:54:28
所以我在字符串中有一个HTML表。这些HTML大多来自FrontPage,因此格式大多不正确。下面是它的快速样本。
<b>Table 1</b>
<table class='class1'>
<tr>
<td>
<p>Procedure Name</td>
<td>
<p>Procedure</td>
</tr>
</table>
<p><b>Table 2</b></p>
<table class='class2'>
<tr>
<td>
<p>Procedure Name</td>
<td>
<p>Procedure</td>
</tr>
</table>
<p> Some text is here</p>
据我所知,FrontPage会自动在每个新单元格中添加一个<p>
。
我想删除那些在表内的<p>
标记,但保留那些在表外的标记。到目前为止,我尝试了两种方法:
第一种方法
第一种方法是使用单个RegEx来捕获表中的每个<p>
标记,然后使用Regex.Replace()
来删除它们。然而,我从来没有找到合适的RegEx。(我知道用RegEx解析HTML很糟糕。我认为数据足够简单,可以应用RegEx(。
使用以下regex:<table.*?>(.*?)</table>
,我可以很容易地获得每个表中的所有内容
然后我只想获取<p>
标签,所以我写了这个:(?<=<table.*?>)(<p>)(?=</table>)
。这与任何内容都不匹配。(显然,.NET允许在其lookbehinds中使用量词。至少这是我在使用时的印象http://regexhero.net/tester/)
有什么办法我可以修改这个RegEx来只捕获我需要的东西吗?
第二种方法
第二种方法是只将表内容捕获到字符串中,然后String.Replace()
删除<p>
标记。我使用以下代码来捕获匹配:
MatchCollection tablematch = Regex.Matches(htmlSource, @"<table.*?>(.*?)</table>", RegexOptions.Singleline);
htmlSource
是一个包含整个HTML页面的字符串,该变量是处理后将发送回客户端的变量。我只想从htmlSource
中删除我需要删除的内容。
如何使用MatchCollection删除<p>
标记,然后将更新后的表发送回htmlSource
?
感谢
这个答案基于第二种建议的方法。更改Regex以将表中的所有内容匹配到:
<table.*?table>
并使用Regex.Replace指定MatchEvaluator来执行所需的替换:
Regex myRegex = new Regex(@"<table.*?table>", RegexOptions.Singleline);
string replaced = myRegex.Replace(htmlSource, m=> m.Value.Replace("<p>",""));
Console.WriteLine(replaced);
使用问题输入的输出:
<b>Table 1</b>
<table class='class1'>
<tr>
<td>
Procedure Name</td>
<td>
Procedure</td>
</tr>
</table>
<p><b>Table 2</b></p>
<table class='class2'>
<tr>
<td>
Procedure Name</td>
<td>
Procedure</td>
</tr>
</table>
<p> Some text is here</p>
我想通过使用委托(回调(可以完成。
string html = @"
<b>Table 1</b>
<table class='class1'>
<tr>
<td>
<p>Procedure Name</td>
<td>
<p>Procedure</td>
</tr>
</table>
<p><b>Table 2</b></p>
<table class='class2'>
<tr>
<td>
<p>Procedure Name</td>
<td>
<p>Procedure</td>
</tr>
</table>
<p> Some text is here</p>
";
Regex RxTable = new Regex( @"(?s)(<table[^>]*>)(.+?)(</table's*>)" );
Regex RxP = new Regex( @"<p>" );
string htmlNew = RxTable.Replace(
html,
delegate(Match match)
{
return match.Groups[1].Value + RxP.Replace(match.Groups[2].Value, "") + match.Groups[3].Value;
}
);
Console.WriteLine( htmlNew );
输出:
<b>Table 1</b>
<table class='class1'>
<tr>
<td>
Procedure Name</td>
<td>
Procedure</td>
</tr>
</table>
<p><b>Table 2</b></p>
<table class='class2'>
<tr>
<td>
Procedure Name</td>
<td>
Procedure</td>
</tr>
</table>
<p> Some text is here</p>
一般来说,regex允许您使用嵌套结构,它非常丑陋,您应该避免它,但如果您没有其他选项,您可以使用它。
static void Main()
{
string s =
@"A()
{
for()
{
}
do
{
}
}
B()
{
for()
{
}
}
C()
{
for()
{
for()
{
}
}
}";
var r = new Regex(@"
{
(
[^{}] # everything except braces { }
|
(?<open> { ) # if { then push
|
(?<-open> } ) # if } then pop
)+
(?(open)(?!)) # true if stack is empty
}
", RegexOptions.IgnorePatternWhitespace | RegexOptions.ExplicitCapture);
int counter = 0;
foreach (Match m in r.Matches(s))
Console.WriteLine("Outer block #{0}'r'n{1}", ++counter, m.Value);
Console.Read();
}
这里regex"知道"块从哪里开始,从哪里结束,所以如果没有合适的结束标记,您可以使用这些信息来删除<p>
标记。