【问题标题】:Regex XML tags having angle brackets inside内含尖括号的正则表达式 XML 标记
【发布时间】:2016-07-28 08:13:19
【问题描述】:

我需要一个正则表达式,它会给我一个 XML 标签,例如<ABC/><ABC></ABC>

所以,如果我在这里使用<(.)+?>,它会给我<ABC><ABC></ABC>。这很好。

现在,问题来了:

我有一个 XML

<VALUE ABC="10000" PQR="12422700" ADJ="" PROD_TYPE="COCOG EFI LWL P&amp;C >1Y-5Y" SRC="BASE" DATA="data" ACTION="INSERT" ID="100000" GRC_PROD=""/>

在这里,如果您看到,PROD_TYPE="COCOG EFI LWL P&amp;amp;C &gt;1Y-5Y" 在属性值中有一个大于号。

所以,正则表达式返回我

&lt;VALUE ABC="10000" PQR="12422700" ADJ="" PROD_TYPE="COCOG EFI LWL P&amp;amp;C &gt;

而不是完整的

&lt;VALUE ABC="10000" PQR="12422700" ADJ="" PROD_TYPE="COCOG EFI LWL P&amp;amp;C &gt;1Y-5Y" SRC="BASE" DATA="data" ACTION="INSERT" ID="100000" GRC_PROD=""/&gt;

我需要一些正则表达式,它不会考虑作为值的一部分的小于和大于符号,即用双引号括起来。

【问题讨论】:

标签: java regex xml


【解决方案1】:

你可以试试这个:

(?i)<[a-z][\w:-]+(?: [a-z][\w:-]+="[^"]*")*/?>

解释如下:

(?i)         # Match the remainder of the regex with the options: case insensitive (i)
<            # Match the character “<” literally
[a-z]        # Match a single character in the range between “a” and “z”
[\\w:-]       # Match a single character present in the list below
                # A word character (letters, digits, and underscores)
                # The character “:”
                # The character “-”
   +            # Between one and unlimited times, as many times as possible, giving back as needed (greedy)
(?:          # Match the regular expression below
   \\            # Match the character “ ” literally
   [a-z]        # Match a single character in the range between “a” and “z”
   [\\w:-]       # Match a single character present in the list below
                   # A word character (letters, digits, and underscores)
                   # The character “:”
                   # The character “-”
      +            # Between one and unlimited times, as many times as possible, giving back as needed (greedy)
   =\"           # Match the characters “=\"” literally
   [^\"]         # Match any character that is NOT a “\"”
      *            # Between zero and unlimited times, as many times as possible, giving back as needed (greedy)
   \"            # Match the character “\"” literally
)*           # Between zero and unlimited times, as many times as possible, giving back as needed (greedy)
/            # Match the character “/” literally
   ?            # Between zero and one times, as many times as possible, giving back as needed (greedy)
>            # Match the character “>” literally

如果您想包含opencloseself-closed 标签,请尝试以下RegEx

(?i)(?:<([a-z][\w:-]+)(?: [a-z][\w:-]+="[^"]*")*>.+?</\1>|<([a-z][\w:-]+)(?: [a-z][\w:-]+="[^"]*")*/>)

实现相同的java 代码片段:

try {
    boolean foundMatch = subjectString.matches("(?i)(?:<([a-z][\\w:-]+)(?: [a-z][\\w:-]+=\"[^\"]*\")*>.+?</\\1>|<([a-z][\\w:-]+)(?: [a-z][\\w:-]+=\"[^\"]*\")*/>)");
} catch (PatternSyntaxException ex) {
    // Syntax error in the regular expression
}

希望这会有所帮助...

【讨论】:

  • 感谢您的解决方案。我只是将其更改为 (?i)?[az][\w:-]+(?: [az][\w:-]+="[^"]*")*/?>开始时没有检查正斜杠。
  • 很高兴为您提供帮助...但是这样做,它不会一次匹配&lt;ABC&gt;...&lt;/ABC&gt;...!!正如您在问题中提到的...
  • 我不需要将它们合二为一,但需要将它们分开。不管怎么说,多谢拉! :)
【解决方案2】:

扩展 G_H 的链接点:Don't use regex to parse XML. 使用 XPath 返回一个节点,并将该节点传递给身份 Transformer

Node valueElement = (Node)
    XPathFactory.newInstance().newXPath().evaluate("//VALUE",
        new InputSource(new StringReader(xmlDocument)),
        XPathConstants.NODE);

StringWriter result = new StringWriter();
TransformerFactory.newInstance().newTransformer().transform(
    new DOMSource(valueElement), new StreamResult(result));

String valueElementMarkup = result.toString();

【讨论】:

  • +1,不错的方法...虽然尚未测试...顺便说一句,如果xname 包含namesoace...如何处理?
  • @Cylian 我认为"//*[local-name()='VALUE']" 的 XPath 可以解决问题。
  • @Cylian 我不是 .Net 专家,但它确实看起来像 .Net supports it。我不确定您所说的浏览器是什么意思;你说的是 JavaScript 吗?
【解决方案3】:

也试试这个:

&lt;.*?(".*?".*?)*?&gt;

仅当存在偶数个 " 双引号时,它才会抓取 &lt;&gt; 之间的所有内容。成对的双引号表示包含的内容。否则它会跳过&gt; 符号并继续进一步搜索下一个&gt;(这应该在关闭" 引号后发生)

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2015-04-20
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多