仅在内部存在特定标签时才匹配标签

问题描述:

我希望将标签与名称test匹配,但前提是它的名称one中有两个以上标签在importantTag之内。仅在内部存在特定标签时才匹配标签

<test attribute="one"> 
    <unimportantTag> 
     <one>text</one> 
    </unimportantTag> 
    <importantTag> 
     <one>text</one> 
     <one>text</one> 
    </importantTag> 
</test> 

下面这一个不应该被匹配,因为它不具有两个one标签importantTag

<test attribute="one"> 
    <unimportantTag> 
     <one>text</one> 
    </unimportantTag> 
    <importantTag> 
     <one>text</one> 
    </importantTag> 
</test> 
</root> 

我知道,那些那样的东西不应该被解析使用正则表达式,但在这种情况下没有其他办法。
是否有可能使用正则表达式匹配整个测试标签。这个例子被简化了。

根据来自正则表达式的匹配,我想将attribute="one"替换为属性"replaced"

+0

使用HTML/XML解析器请。请从标签列表中删除其中的一个。 – nhahtdh 2014-10-11 15:29:51

+1

http://regex101.com/r/vF9sG0/2 – 2014-10-11 15:41:49

+0

@Avinash Raj - 非常感谢,我已经调整了你的模式,所以它可以在完整的文件上工作,而不是简单的。刚刚还有一个问题。基于这个决定(即找到这个匹配),我想用属性“one”的值替换别的可以说“替换”的单词。既然我看到你在使用非捕获组,是否有任何简单的方法来实现它? – wariacik 2014-10-11 16:19:11

基础上被张贴@Avinash拉吉我建立的,我想一个确切的正则表达式的答案。我是最后的发帖解决方案,也许有人会觉得它有用。

Search pattern: 
(?s)(test)([^<>]*?)(attribute="one")(([^<>]*?)(?:(?!<\/test>).)*<importantTag>(?:(?!<\/test>|<\/importantTag>).)*<one>[^<>]*<\/one>[^<>]*<one>[^<>]*<\/one>(?:(?!<\/test>|<\/importantTag>).)*<\/importantTag>(?:(?!<\/test>).)*)<\/test> 

Replace pattern: 
$1$2attribute="replaced"$4>$5</test> 

http://regex101.com/r/wU2pT9/1

** **修改
尝试这种模式

<test(?=(?:[^<]|<(?!\/test>))*<importantTag>(?=(?:(?:[^<]|<(?!\/test>))*<one>[^<]*<\/one>){2}))(?:[^<]|<(?!\/test>))*<\/test> 

Demo

+0

http://regex101.com/r/yW4aZ3/23 – vks 2014-10-11 16:06:56

+0

@ vks,你是对的,修改我的模式上面,谢谢指出 – 2014-10-11 21:01:42