在过去的两天里我一直在努力解决这个问题。。。你知道吗
请帮助我理解为什么会这样。我的意图是只选择具有<DTL1 val="92">.....</HDR>
的<HDR>
这是我的正则表达式
(?<=<HDR>).*?<DTL1\sval="3".*?</HDR>
输入字符串为:
<HDR>abc<DTL1 val="1"><DTL2 val="2"></HDR><HDR><DTL1 val="92"><DTL2 val="55"></HDR><HDR><DTL1 val="3"><DTL2 val="4"></HDR>
但是这个正则表达式选择
abc<DTL1 val="1"><DTL2 val="2"></HDR><HDR><DTL1 val="92"><DTL2 val="55"></HDR>
有人能帮我吗?你知道吗
卡西米尔和希波莱特已经给了你一些好的解决方案。我想详细说明几件事。你知道吗
首先,您的正则表达式为什么不能做您想做的事情:
(?<=<HDR>).*?
告诉它匹配任何数量的字符,从前面的第一个字符开始,直到它遇到非贪婪量词(<DTL1...
)后面的字符。好的,前面加<HDR>
的第一个字符是第一个a
,所以它匹配从那里开始的所有内容,直到遇到固定字符串<DTL1\sval="3"
。你知道吗Casimir et Hippolyte的解决方案适用于一般情况,<;HDR>;标记的内容可以是嵌套的<;HDR>;以外的任何内容。您也可以通过积极的前瞻性来实现这一点:
但是,如果字符串保证在所示的结构中,<;HDR>;标记只包含一个或多个<;DTL1 val=“##”>;标记,那么您知道其中不会有任何结束标记,您可以更有效地将第一个
.*?
替换为[^/]*
:否定字符类比零宽度断言更有效,如果使用的是否定字符类,贪婪的量词将比懒惰的量词更有效。你知道吗
另请注意,通过使用lookback匹配开头<;HDR>;,您将其从匹配中排除,但您将包括结尾<;/HDR>;。你确定这就是你想要的吗?你在匹配这个。。。你知道吗
…当你想要这个的时候。。。你知道吗
…或者这个。。。你知道吗
所以,在第一种情况下,不要使用lookback作为开始标记:
在第二种情况下,对结束标记使用前瞻:
正则表达式引擎将始终为您提供字符串中最左边的匹配(即使您使用非贪婪量词)。这正是你得到的。你知道吗
因此,一个解决方案是禁止在
.*?
所描述的部分中存在另一个<HDR>
过于允许。你知道吗有两种方法可以做到这一点,可以用以下方法替换
.*?
:或与:
大多数情况下,第一种技术的性能更高,但是如果字符串包含高密度的
<
,那么第二种方法也可以得到很好的结果。你知道吗使用possessive quantifier或atomic group可以减少获得结果的步骤数,特别是在子模式失败时。你知道吗
示例:
第一种方式:
或此变体:
用第二种方法:
或此变体:
相关问题 更多 >
编程相关推荐