仅从字符串标签中提取值

时间:2019-09-10 18:23:02

标签: java regex string

我正在尝试从给定的字符串中提取值,该值可能包含许多带有该模式的标记,例如

<element1>content1</element1><element2>content2</element2><element3>content3</element3>... and so on.

当前这是我正在使用的带有正则表达式的代码。

String tempString = "<element1>content1</element1><element2>content2</element2>";
String[] tempArray = tempString.split("(<\\w+>)|(</\\w+>)");

for (String item : tempArray) {
    System.out.println("Item: " + item);
}

我期望的结果是:

Item: content1
Item: content2

etc...

相反,我收到:

Item: 
Item: content1
Item:
Item: content2

我只想使用一种划线-一种魔术正则表达式来消除这些空元素。我的意思是-在给定的字符串上,我将该表达式作为一行应用,并且神奇地我在数组中收到了期望的值-无需进一步处理或分组。 甚至有可能实现吗?

4 个答案:

答案 0 :(得分:3)

您可以利用捕获组的反向引用和惰性量词来动态获取所有内容:

<(element\d+)>(.*?)<\/\1>
  • <(element\d+)>-找到一个名为“ element”的标签,后跟至少一个数字,并将其放入$1(例如element1
  • (.*?)-懒惰地将所有内容捕获到$2中,直到下一条正则表达式指令成功
  • <\/\1>-使用\1引用我们在$1中捕获的内容,并将其作为结束标记进行匹配

$2将包含:

content1
content2
content3

https://regex101.com/r/NAImHv/1/

您可以使用Java - Extract strings with Regex使我的正则表达式适合Java代码。


免责声明:正则表达式绝对是错误的工具,您绝对应该研究XPath,但这是一个快速解决问题的方法,如果您可以避免遇到极端情况的话。 >

答案 1 :(得分:0)

使用现有的代码片段,您可以使用一些正则表达式应用以下代码来实现它。 看看下面的代码

导入正则表达式实用程序

import java.util.regex.Matcher;
import java.util.regex.Pattern;

String pattern = "\\w+";
Pattern r = Pattern.compile(pattern);
String tempString =
  "<element1>content1</element1><element2>content2</element2>";
String[] tempArray = tempString.split ("(<\\w+>)|(</\\w+>)");
for (String item:tempArray)
  {
      Matcher matcher = r.matcher(item);
      //check if the pattern matches 
      if(matcher.matches()){
          System.out.println ("Item: " + item);
      }
  }

希望这会有所帮助

谢谢

答案 2 :(得分:0)

如果可以使用流,则可以使用正则表达式,然后过滤掉空的正则表达式:

String tempString = "<element1>content1</element1><element2>content2</element2>";
String[] tempArray = Pattern.compile("(<\\w+>)|(</\\w+>)").splitAsStream(tempString)
                            .filter(s -> !s.isEmpty()).toArray(String[]::new);
System.out.println(Arrays.toString(tempArray));

答案 3 :(得分:0)

另一种解决方案是使用Xpath:

import java.io.IOException;
import java.io.StringReader;
import javax.xml.parsers.DocumentBuilder;
import javax.xml.parsers.DocumentBuilderFactory;
import javax.xml.parsers.ParserConfigurationException;
import javax.xml.xpath.XPath;
import javax.xml.xpath.XPathConstants;
import javax.xml.xpath.XPathFactory;

import org.w3c.dom.Document;
import org.w3c.dom.Node;
import org.w3c.dom.NodeList;

import javax.xml.xpath.XPathExpression;
import javax.xml.xpath.XPathExpressionException;

import org.xml.sax.InputSource;
import org.xml.sax.SAXException;

public class Extract {

    public static void main(String[] args) throws ParserConfigurationException, SAXException, IOException, XPathExpressionException {
        // Q 57876359

        DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance();
        factory.setNamespaceAware(true);
        DocumentBuilder builder = factory.newDocumentBuilder();

        String xml = new String("<?xml version=\"1.0\" encoding=\"UTF-8\"?>\r\n" + 
                "<elements>\r\n" + 
                "   <element1>content1</element1>\r\n" + 
                "   <element2>content2</element2>\r\n" + 
                "   <element3>content3</element3>\r\n" + 
                "</elements>");
        InputSource is = new InputSource(new StringReader(xml));
        Document doc = builder.parse(is);   
        XPathFactory xpathfactory = XPathFactory.newInstance();
        XPath xpath = xpathfactory.newXPath();

        int nodes = doc.getChildNodes().getLength();    

        NodeList nodeList = doc.getChildNodes();    
        //To get <elements> root node
        Node firstNode = nodeList.item(0);

        //To get childs element0...elementN
        NodeList elementNodes = firstNode.getChildNodes();

        //Last node is a text node
        Node lastInnerNode = elementNodes.item(elementNodes.getLength()-2);

        //To extract index of last tag
        String lastInnerNodeName = lastInnerNode.getNodeName(); 
        int lastNodeIndex =  Integer.parseInt(lastInnerNodeName.substring(lastInnerNodeName.length()-1, lastInnerNodeName.length()));

        XPathExpression xpathexpression;

        //To extract every content
        for (int i = 1; i <= lastNodeIndex; i++) {
            xpathexpression = xpath.compile("//element"+i+"/text()");
            Object result = xpathexpression.evaluate(doc, XPathConstants.STRING);
            String texto = (String) result;
            System.out.println("Item: "+texto);
        }
  }