我有以下html代码,它们嵌套到3级:
<div class="sp-wrap">
<div class="sp-body" title="FAQ">
Some text
<div class="sp-wrap">
<div class="sp-body" title="title1"> // Level 2
Text1...
</div>
</div>
<div class="sp-wrap">
<div class="sp-body" title="title2"> // Level 2
Text2...
</div>
</div>
<div class="sp-wrap">
<div class="sp-body" title="title3"> // Level 2
Text3...
<div class="sp-wrap">
<div class="sp-body" title="title4"> // Level 3
Text4...
</div>
</div>
</div>
</div>
</div>
我需要将div标签替换为bbcode,而我的正则表达式只能用于非嵌套的剧透:
Regex.Replace(outstring,
@"<div class=""sp-body"" title=""(.*?)"">(.*?)</div>",
"[spoiler=$1]$2[/spoiler]",
RegexOptions.Singleline);
答案 0 :(得分:0)
你的代码的问题是它只会替换第一次出现的div和下一个最接近/ div出现的div
<div> // replaced
<div> // not replaced
</div> // replaced
</div> // not replaced
一种方法是将其加载到XML中,然后仅使用XPATH修改您感兴趣的节点。如果是HTML,您还可以使用HTML解析器,然后使用CSS选择器。
您可以轻松修改开场div(通过与类匹配),但正则表达式无法知道哪个是相应的结尾div。
答案 1 :(得分:0)
没有测试,但这个想法应该有效:
string s1 = Regex.Replace(outstring, @"<div class=""sp-body"" title=""(.*?)"">", "[spoiler=$1]", RegexOptions.Singleline);
string s2 = Regex.Replace(s1, @"</div>", "[/spoiler]", RegexOptions.Singleline);
修改强>
string s1 = Regex.Replace(outstring, @"<div class=""sp-wrap"">\s*<div class=""sp-body"" title=""(.*?)"">", "[spoiler=$1]", RegexOptions.Singleline);
string s2 = Regex.Replace(s1, @"</div>\s*</div>", "[/spoiler]", RegexOptions.Singleline);
应该产生类似
的东西[spoiler=FAQ]
Some text
[spoiler=title1] // Level 2
Text1...
[/spoiler]
[spoiler=title2] // Level 2
Text2...
[/spoiler]
[spoiler=title3] // Level 2
Text3...
[spoiler=title4] // Level 3
Text4...
[/spoiler]
[/spoiler]
</div>
正如你所看到的那样,它并没有完美缩进(可以修复,我猜)并且在示例中检测到一个缺失</div>
。
答案 2 :(得分:0)
使用Regex方法尚未完全完成此任务。使用Html Agility Pack解析Html
答案 3 :(得分:0)
为你的正则表达式制作一个循环:
var rgx = new Regex(@"<div class=""sp-body"" title=""(.*?)"">(.*?)</div>");
while (rgx.IsMatch(outstring))
{
outstring = rgx.Replace(outstring, "[spoiler=$1]$2[/spoiler]");
}