zoukankan      html  css  js  c++  java
  • Java核心技术II读书笔记(一)

    Char2 XML

    解析器:读入一个文件,确认其具有正确的格式,然后将其分解成各种元素,使程序员能够访问这些元素。

    java库提供了两种XML解析器:DOM和SAX,即文档对象模型和流机制解析器。

    DOM不适合处理太长的XML,考虑到内存的消耗。

    如果只对XML中的某些元素感兴趣,而不关心上下文,考虑用SAX。

    DOM解析器的接口已经被W3C标准化了,org.w3c.dom包中包含了这些接口类型的定义,比如Document和Element等。不同的组织都提供了实现这些接口的DOM解析器,如Apache和IBM。我们可以通过JAXP(Java API for XML Processing)库以插件的方式使用这些解析器中的任意一个。JDK本身也有自己的DOM解析器。本章就使用这个。所以,我们只要通过实现以上的接口或类就能达到使用解析器的目的。

    以下是读入一个XML文档的方式:

    DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance();

    DocumentBuilder builder = factory.newDocumentBuilder();  //这个就是解析器对象啦

    书里说了三种XML的来源,File、URL、InputStream:

    FIle f = ...

    Document doc = builder.parse(f);

    URL u = ...

    Document doc = builder.parse(u);

    InputStream in = ...

    Document doc = builder.parse(in);

    需要注意的是,如果以InputStream为输入源,当XML中有用到DTD等以该XML的位置为相对路径的引用时,解析器将无法定位这个DTD等文档。需要安装一个“实体解析器”(entity resolver)来解决这个问题。

    接下来就是解析Document对象各个部分的事了,具体看这个图:

    例如,处理下面的文档:

    <?xml version="1.0"?>

    <font>

         <name>Zhangsan</name>

         <size>33</size>

    </font>

    Element root = doc.getDocumentElement();  //返回根元素font

    root.getTagName();   //返回字符串"font"

    获得该元素的子元素:

    NodeList children = root.getChildNodes();

    for(int i=0;i<children.getLength();i++){

        Node child = children.item(i);

        ...

    }

    其中,getLength()=5而不是2,为啥?因为子元素与主元素之间、子元素与子元素之间空格也算了。如果只希望得到子元素,可以这样处理:

    NodeList children = root.getChildNodes();

    for(int i=0;i<children.getLength();i++){

        Node child = children.item(i);

        if(child instanceof Element){

            Element childElement = (Element)child;

            ...

        }

    }

    这样处理还是很麻烦的,这就是为啥后面要引入DTD的原因了,DTD能后对XML的内容进行规范处理,减少一些不必要的验证过程。

    我们看上面的图,其中包括空白子元素,是Text类型的,另外,发现没?name和size的值也是Text类型的,所以,怎么样获得Zhangsan、33这两个值呢?自然通过Text类型的对象来处理:

    for(int i=0;i<children.getLength();i++){

           Node child = children.item(i);

           if(child instanceof Element){

                  Element childElement = (Element) child;

                  Text textNode = (Text) childElement.getFirstChild();

                  String text = textNode.getData().trim();   

                  if(childElement.getTagName().equals("name")){

                         name = text;

                  }else if(childElement.getTagName().equals(size")){

                         size = Integer.parseInt(text);

                  }

           }

    }

    上面用到trim()是为了避免下面格式产生的空格:

    <size>

         33

    </size>

    这种情况下,解析器会把所有的换行符和空格都包含到Text中去。

    最后一部分是获取XML中元素属性对象,直接上代码:

    NameNodeMap attributes = element.getAttributes();

    for(int i=0;i<attributes.getLength();i++){

      Node attribute = attributes.item(i);

      String name = attribute.getNodeName();    //属性名

      String value = attribute.getNodeValue();     //属性值

    }

  • 相关阅读:
    P1273 有线电视网
    P2015 二叉苹果树
    POJ 3659 Cell Phone Network
    POJ 1463 Strategic game
    NC51178 没有上司的舞会
    NC15033 小G有一个大树
    13. SpringBoot 日志框架的默认配置 和 指定日志文件 以及 ProFile 功能
    12. SpringBoot 日志框架的关系 研究中间包的替换
    11. SpringBoot 日志框架 — 解决和思路
    41.el和template区别 & VUE实现分离写法
  • 原文地址:https://www.cnblogs.com/runwulingsheng/p/5417913.html
Copyright © 2011-2022 走看看