JAVA 는 XPath 를 통 해 XML 성능 을 분석 하 는 것 이 비교적 상세 하 다.

13579 단어 자바xpath
최근 XML 파일 분석 기술 에 사용 되 는 작은 프로젝트 를 만 들 고 있 으 며,이 기술 에 대한 이해 와 사용 을 통 해 다음 과 같은 내용 을 정리 했다.
1 XML 파일 을 분석 하 는 네 가지 방법
보통 XML 파일 을 해석 하 는 데 는 네 가지 고전적 인 방법 이 있다.기본 적 인 해석 방식 은 두 가지 가 있 는데 하 나 는 SAX 이 고 다른 하 나 는 DOM 이다.SAX 는 이벤트 흐름 에 기반 한 해석 이 고 DOM 은 XML 문서 트 리 구조 에 기반 한 해석 입 니 다.여기에 더 해 DOM,SAX 의 인 코딩 량 을 줄 이기 위해 JDOM 이 나 왔 는데,20~80 원칙(파 르 토 법칙)으로 인 코딩 량 을 크게 줄 였 다 는 장점 이 있다.일반적인 상황 에서 JDOM 은 사용 할 때 실현 하고 자 하 는 기능 이 간단 하 다.예 를 들 어 해석,생 성 등 요 구 를 만족시킨다.그러나 밑바닥 에 서 는 JDom 이 SAX(가장 많이 사용),DOM,Xanan 문 서 를 사용한다.또 하 나 는 DOM4J 로 매우 우수한 자바 XML API 로 성능 이 우수 하고 기능 이 강하 며 사용 하기 쉬 운 특징 을 가지 고 있 으 며 소스 코드 를 개방 하 는 소프트웨어 이기 도 하 다.이제 점점 더 많은 자바 소프트웨어 가 DOM4J 를 사용 하여 XML 을 읽 고 쓰 는 것 을 볼 수 있다.특히 Sun 의 JAXM 도 DOM4J 를 사용 하고 있다.
2 XPath 간단 한 소개
XPath 는 XML 문서 에서 정 보 를 찾 는 언어 입 니 다.XPath 는 XML 문서 에서 요소 와 속성 을 통 해 탐색 하고 요소 와 속성 을 옮 겨 다 니 는 데 사 용 됩 니 다.XPath 는 W3C XSLT 표준 의 주요 요소 이 고 XQuery 와 XPointer 는 동시에 XPath 표현 위 에 구축 되 었 다.따라서 XPath 에 대한 이 해 는 많은 고급 XML 응용의 기초 이다.XPath 는 데이터 베 이 스 를 조작 하 는 SQL 언어 나 JQuery 와 매우 유사 하여 개발 자가 문서 에 필요 한 것 을 쉽게 잡 을 수 있 습 니 다.이 가운데 DOM4J 도 XPath 사용 을 지원 한다.
3 DOM4J 는 XPath 를 사용한다.
DOM4J 는 XPath 를 사용 하여 XML 문 서 를 해석 합 니 다.먼저 프로젝트 에서 두 개의 JAR 패 키 지 를 참조 해 야 합 니 다.
dom4j-1.6.1.jar:DOM4J 패키지,다운로드 주소http://sourceforge.net/projects/dom4j/;
jaxen-xx.xx.jar:이 가방 을 추가 하지 않 으 면 이상 이 발생 합 니 다(java.lang.NoClassDef Foundation Error:org/jaxen/Jaxen Exception).다운로드 주소http://www.jaxen.org/releases.html
3.1 네 임 스페이스(namespace)의 간섭
엑셀 파일 이나 다른 형식 파일 로 변 환 된 xml 파일 을 처리 할 때 보통 XPath 를 통 해 결 과 를 분석 하지 못 하 는 경우 가 있 습 니 다.이런 상황 은 보통 네 임 스페이스 의 존재 로 인 한 것 이다.다음 내용 의 XML 파일 의 경우 XPath='/Workbook/Worksheet/Table/Row[1]/Cell[1]/Data[1]'를 통 해 간단하게 검색 하면 결과 가 나 오지 않 는 경우 가 많다.이것 은 네 임 스페이스 namespace(xmlns="urn:schemas-microsoft-com:office:spreadsheet")로 인 한 것 입 니 다.

<Workbook xmlns="urn:schemas-microsoft-com:office:spreadsheet" xmlns:o="urn:schemas-microsoft-com:office:office" xmlns:x="urn:schemas-microsoft-com:office:excel" xmlns:ss="urn:schemas-microsoft-com:office:spreadsheet" xmlns:html="http://www.w3.org/TR/REC-html40">
 <Worksheet ss:Name="Sheet1">
  <Table ss:ExpandedColumnCount="81" ss:ExpandedRowCount="687" x:FullColumns="1" x:FullRows="1" ss:DefaultColumnWidth="52.5" ss:DefaultRowHeight="15.5625">
   <Row ss:AutoFitHeight="0">
     <Cell>
     <Data ss:Type="String">      </Data>
     </Cell> 
   </Row>
   <Row ss:AutoFitHeight="0">
     <Cell>
     <Data ss:Type="String">Sunny</Data>
     </Cell> 
   </Row>
  </Table>
 </Worksheet>
</Workbook>
3.2 XPath 는 네 임 스페이스 가 있 는 xml 파일 에 대한 분석
첫 번 째 방법(read 1()함수):XPath 문법 에 있 는 local-name()과 namespace-uri()를 사용 하여 사용 할 노드 이름과 네 임 스페이스 를 지정 합 니 다.XPath 표현 식 은 쓰기 가 비교적 번거롭다.
두 번 째 방법(read 2()함수):XPath 의 네 임 스페이스 를 설정 하고 setNamespaceURis()함 수 를 이용 합 니 다.
세 번 째 방법(read 3()함수):DocumentFactory()의 네 임 스페이스 를 설정 합 니 다.사용 하 는 함 수 는 setXPath NamespaceURI()입 니 다.두 가지 와 세 가지 방법의 XPath 표현 식 은 쓰기 가 상대 적 으로 간단 하 다.
네 번 째 방법(read 4()함수):방법 은 세 번 째 와 같 지만 XPath 표현 식 이 다 릅 니 다.주로 XPath 표현 식 이 다 르 고 완전 도 를 가리 키 며 검색 효율 에 영향 을 미 치 는 지 검증 하기 위해 서 입 니 다.(위의 네 가지 방법 은 모두 DOM4J 와 XPath 를 결합 하여 XML 파일 을 분석 합 니 다)
다섯 번 째 방법(read 5()함수):DOM 과 XPath 를 결합 하여 XML 파일 을 분석 하 는데 주로 성능 차 이 를 검증 하기 위 한 것 입 니 다.
코드 만큼 문 제 를 설명 할 수 있 는 것 은 없다!코드 과감하게!

package XPath;
import java.io.IOException;
import java.io.InputStream;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import javax.xml.parsers.DocumentBuilder;
import javax.xml.parsers.DocumentBuilderFactory;
import javax.xml.parsers.ParserConfigurationException;
import javax.xml.xpath.XPathConstants;
import javax.xml.xpath.XPathExpression;
import javax.xml.xpath.XPathExpressionException;
import javax.xml.xpath.XPathFactory;

import org.dom4j.Document;
import org.dom4j.DocumentException;
import org.dom4j.Element;
import org.dom4j.XPath;
import org.dom4j.io.SAXReader;
import org.w3c.dom.NodeList;
import org.xml.sax.SAXException;

/**
 * DOM4J DOM XML XPath
 * @author hao
 */
public class TestDom4jXpath {
  public static void main(String[] args) {
    read1();
    read2();
    read3();
    read4();//read3()    ,  XPath     
    read5();
  }
  
  public static void read1() {
    /*
     * use local-name() and namespace-uri() in XPath
     */
    try {
      long startTime=System.currentTimeMillis();
      SAXReader reader = new SAXReader();
      InputStream in = TestDom4jXpath.class.getClassLoader().getResourceAsStream("XPath\\XXX.xml");
      Document doc = reader.read(in);
      /*String xpath ="//*[local-name()='Workbook' and namespace-uri()='urn:schemas-microsoft-com:office:spreadsheet']"
          + "/*[local-name()='Worksheet']"
          + "/*[local-name()='Table']"
          + "/*[local-name()='Row'][4]"
          + "/*[local-name()='Cell'][3]"
          + "/*[local-name()='Data'][1]";*/
      String xpath ="//*[local-name()='Row'][4]/*[local-name()='Cell'][3]/*[local-name()='Data'][1]";
      System.err.println("=====use local-name() and namespace-uri() in XPath====");
      System.err.println("XPath:" + xpath);
      @SuppressWarnings("unchecked")
      List<Element> list = doc.selectNodes(xpath);
      for(Object o:list){ 
        Element e = (Element) o; 
        String show=e.getStringValue();
        System.out.println("show = " + show); 
      long endTime=System.currentTimeMillis();
      System.out.println("      : "+(endTime-startTime)+"ms");
      } 
    } catch (DocumentException e) {
      e.printStackTrace();
    }
  }
  
  public static void read2() {
    /*
     * set xpath namespace(setNamespaceURIs)
     */
    try {
      long startTime=System.currentTimeMillis();
      Map map = new HashMap();
      map.put("Workbook","urn:schemas-microsoft-com:office:spreadsheet");
      SAXReader reader = new SAXReader();
      InputStream in = TestDom4jXpath.class.getClassLoader().getResourceAsStream("XPath\\XXX.xml");
      Document doc = reader.read(in);
      String xpath ="//Workbook:Row[4]/Workbook:Cell[3]/Workbook:Data[1]";
      System.err.println("=====use setNamespaceURIs() to set xpath namespace====");
      System.err.println("XPath:" + xpath);
      XPath x = doc.createXPath(xpath);
      x.setNamespaceURIs(map);
      @SuppressWarnings("unchecked")
      List<Element> list = x.selectNodes(doc);
      for(Object o:list){ 
        Element e = (Element) o; 
        String show=e.getStringValue();
        System.out.println("show = " + show);  
      long endTime=System.currentTimeMillis();
      System.out.println("      : "+(endTime-startTime)+"ms");
      } 
    } catch (DocumentException e) {
      e.printStackTrace();
    }
  }
  
  public static void read3() {
    /*
     * set DocumentFactory() namespace(setXPathNamespaceURIs)
     */
    try {
      long startTime=System.currentTimeMillis();
      Map map = new HashMap();
      map.put("Workbook","urn:schemas-microsoft-com:office:spreadsheet");
      SAXReader reader = new SAXReader();
      InputStream in = TestDom4jXpath.class.getClassLoader().getResourceAsStream("XPath\\XXX.xml");
      reader.getDocumentFactory().setXPathNamespaceURIs(map);
      Document doc = reader.read(in);
      String xpath ="//Workbook:Row[4]/Workbook:Cell[3]/Workbook:Data[1]";
      System.err.println("=====use setXPathNamespaceURIs() to set DocumentFactory() namespace====");
      System.err.println("XPath:" + xpath);
      @SuppressWarnings("unchecked")
      List<Element> list = doc.selectNodes(xpath);
      for(Object o:list){ 
        Element e = (Element) o; 
        String show=e.getStringValue();
        System.out.println("show = " + show);
      long endTime=System.currentTimeMillis();
      System.out.println("      : "+(endTime-startTime)+"ms");  
      } 
    } catch (DocumentException e) {
      e.printStackTrace();
    }
  }
  
  public static void read4() {
    /*
     *  read3()    ,  XPath     
     */
    try {
      long startTime=System.currentTimeMillis();
      Map map = new HashMap();
      map.put("Workbook","urn:schemas-microsoft-com:office:spreadsheet");
      SAXReader reader = new SAXReader();
      InputStream in = TestDom4jXpath.class.getClassLoader().getResourceAsStream("XPath\\XXX.xml");
      reader.getDocumentFactory().setXPathNamespaceURIs(map);
      Document doc = reader.read(in);
      String xpath ="//Workbook:Worksheet/Workbook:Table/Workbook:Row[4]/Workbook:Cell[3]/Workbook:Data[1]";
      System.err.println("=====use setXPathNamespaceURIs() to set DocumentFactory() namespace====");
      System.err.println("XPath:" + xpath);
      @SuppressWarnings("unchecked")
      List<Element> list = doc.selectNodes(xpath);
      for(Object o:list){ 
        Element e = (Element) o; 
        String show=e.getStringValue();
        System.out.println("show = " + show);
      long endTime=System.currentTimeMillis();
      System.out.println("      : "+(endTime-startTime)+"ms");  
      } 
    } catch (DocumentException e) {
      e.printStackTrace();
    }
  }
  
  public static void read5() {
    /*
     * DOM and XPath
     */
    try {
      long startTime=System.currentTimeMillis();
      DocumentBuilderFactory dbf = DocumentBuilderFactory.newInstance();
      dbf.setNamespaceAware(false);
      DocumentBuilder builder = dbf.newDocumentBuilder();
      InputStream in = TestDom4jXpath.class.getClassLoader().getResourceAsStream("XPath\\XXX.xml");
      org.w3c.dom.Document doc = builder.parse(in);
      XPathFactory factory = XPathFactory.newInstance();
      javax.xml.xpath.XPath x = factory.newXPath();
      //    class   name  
      String xpath = "//Workbook/Worksheet/Table/Row[4]/Cell[3]/Data[1]";
      System.err.println("=====Dom XPath====");
      System.err.println("XPath:" + xpath);
      XPathExpression expr = x.compile(xpath);
      NodeList nodes = (NodeList)expr.evaluate(doc, XPathConstants.NODE);
      for(int i = 0; i<nodes.getLength();i++) {
        System.out.println("show = " + nodes.item(i).getNodeValue());
      long endTime=System.currentTimeMillis();
      System.out.println("      : "+(endTime-startTime)+"ms");
      }
    } catch(XPathExpressionException e) {
      e.printStackTrace();
    } catch(ParserConfigurationException e) {
      e.printStackTrace();
    } catch(SAXException e) {
      e.printStackTrace();
    } catch(IOException e) {
      e.printStackTrace();
    }
  }
}

3.3 서로 다른 방법의 성능 비교
몇 가지 방법의 해석 성능 을 비교 하기 위해 실험 과정 에서 6M 이상 의 크기 를 사 용 했 고 7 만 줄 이상 의 XML 파일(XXX.xml)을 사용 하여 10 차례 의 테스트 를 실시 했다.다음 과 같다.

그림 1 XPath 사용 성능 비교
방법 이름
평균 운행 시간
XPath 표현 식
read1()
1663ms
//*[local-name()='Row'][4]/*[local-name()='Cell'][3]/*[local-name()='Data'][1]
read2()
2184ms
//Workbook:Row[4]/Workbook:Cell[3]/Workbook:Data[1]
read3()
601ms
//Workbook:Row[4]/Workbook:Cell[3]/Workbook:Data[1]
read4()
472ms
//Workbook:Worksheet/Workbook:Table/Workbook:Row[4]/Workbook:Cell[3]/Workbook:Data[1]
read5()
1094ms
//Workbook/Worksheet/Table/Row[4]/Cell[3]/Data[1]
표 1 평균 성능 통계
이상 의 성능 비교 에서 알 수 있 듯 이:
1.read 4()방법 은 실행 시간 이 가장 짧 습 니 다.즉,DOM4J 방법 으로 전체 경 로 를 호출 하 는 것 입 니 다(루트 노드 에서 출발)XPath 표현 식 으로 XML 파일 을 분석 하 는 데 가장 짧 은 시간 이 걸 립 니 다.
2.DOM 해석 방법 을 사용 하여 사용 하 는 XPath 표현 식 이 가장 간단 합 니 다(쓰기//Row[4]/Cell[3]/Data[1]).DOM 에서 setNamespaceAware(false)방법 으로 네 임 스페이스 를 무효 화 할 수 있 기 때 문 입 니 다.
이상 이 바로 본 고의 모든 내용 입 니 다.여러분 의 학습 에 도움 이 되 고 저 희 를 많이 응원 해 주 셨 으 면 좋 겠 습 니 다.

좋은 웹페이지 즐겨찾기