我有以下情况, 我需要改变,
<a href="ab/xyz" onclick="ab/123"></a>
到
<a href="pq/xyz" onclick="pq/123"></a>
每当“ab”出现在html标签的属性值中时,基本上将“ab”替换为“pq”
我写了以下正则表达式,
(<[^>]+)((=")(ab)([^>/"]*"))+([^>].*>)
我正在做replaceAll
if(matcher.find())
matcher.ReplaceAll($1$3pq$4$5)
上面的代码只替换了每个标签的一个属性值,即使我的正则表达式中有重复运算符而且我正在执行ReplaceAll
如果我将“if”条件更改为while循环,那么它会更改所有属性,基本上每次迭代1个属性
有没有办法在没有循环的情况下替换所有属性值中的所有匹配项?
解决方案:即使没有重复运算符,一个愚蠢的正则表达式也在做这个技巧。问题是我匹配整个标签。
答案 0 :(得分:0)
它只替换了一次出现,因为最后的.*
与你的搅拌的整个长度匹配(好吧,直到最后>
的所有内容,但很可能是文档的结尾因为它将以html>
结束 - 并且背后没有其他匹配。
Java支持前瞻和后瞻,我们需要那些才能使它工作。基本上,前瞻告诉Java“只有在匹配后跟着什么匹配才匹配,但不管是匹配本身的一部分”。 Lookbehinds是相同的,只是在比赛之前必须有的东西。不幸的是,Java在lookbehinds中不支持*
和+
,所以它们有点棘手,但它应该有效:
([^>]*?="[^"]*?)ab(?=[^<]*>)
将其替换为$1pq
。
我测试了它,它可以工作 - 但只替换每个属性(第一个)中的一个ab
。如果你在一个属性中有多个ab
并且所有shoudl都被替换,我认为没办法(没有适当的lookbehinds)
请注意,这是假设有效的HTML - 它可能会在无效的HTML上产生意外结果。