java的XML文件解析器

        对于java的文件的存在形式,最重要的有txt与xml两种。对于txt格式文件,一般就放在项目文件夹下,也就是跟配置文件同等级,而对于XML文件则是放在src文件夹下(src文件夹就是资源文件的意思),txt文件使用File类的相关类就可以进行读写,而XML在src文件夹下则是使用projectname.class.getClassLoader().getResourceAsStream()进行资源读取,但是在写的时候则不大一样,其实txt文件放在src文件夹下不能写,而XML文件也是不行。这个问题估计是因为src文件夹是资源文件夹的缘故。

        其实真正的问题也就是XML文件的读写而已。所以java有好些XML文件解析器,大致上有SAX,DOM,DOM4J,JDOM,JAXP等。

        其实所有的解析器都是源于SAX与DOM的,同时后面发展出的解析器各有所长但是同样的存在缺陷。

        注意,SAX使用中,含有Document标志的方法就是操作整个XML文件的方法,而含有Element标志的方法就是操作<xxx key=value>xx<xxx/>字符串的方法。但是DOM的则有点不一样,在得到Document之后,使用Document.getDocumentElement()得到继承自Node的Element实例对象,这里Element实际上使用的最多的是Node的方法,所以最关键点就在于Node的定义及方法。这里Node在解析中代表<xxx key=value>xx<xxx/>节点字符串,在使用Node.getAttributes().item()中代表key=value字符串。这里需要注意,在解析中DOM使用<,>作为分隔符分割节点字符串,所以就连空白符都会是Node节点,所以我们在操作节点时需要考虑空白符的存在。而在DOM的Node.getAttributes()中解析使用空白符作为分隔符,而空白符作为分隔符被忽略了,所以使用Node.getAttributes()得到的NamedNodeMap中包含的Node并不存在空白符,所以我们就可以不用考虑空白符的存在了。同时注意使用Node.getNodeType(),Node.getNodeName(),Node.getNodeValue()在解析key=value中Node.getNodeName(),得到的是key,Node.getNodeValue()得到的是value;而如果是<xxx key=value>xx<xxx/>形式的则Node.getNodeName()得到的是xxx,而Node.getNodeValue()返回null。

        注意,DOM解析关键方法在于Document.getDocumentElement(),Node.getNextSibling(),Node.getChildNodes(),Node.getAttributes(),常用方法就是Node.getNodeType(),Node.getNodeName(),Node.getNodeValue(),这里Node.getNodeType()用于判断节点类型,例如Node.ELEMENT_NODE,Node.TEXT_NODE这两种类型就分别对应了上面的两种情况Node.ELEMENT_NODE对应<xxx key=value>xx<xxx/>形式,Node.TEXT_NODE对应key=value形式。

        对于DOM解析中纯字符甚至是空白字符的Node节点可以使用Node.getTextContent()得到内容。

        至于PULL解析,其实反而是最简单的。Pull解析是以<,>为分割符的,所以同样需要考虑空白符的存在,也就是说空白符被当成解析元素处理。这里Pull解析每一种解析元素都有对应的常量对应。实际使用中,我们使用getName(),getAttributeName(),getAttributeValue(),getText(),next()等方法来得到想要的。next()可以移动到下一个元素。getName()可以得到元素名,例如<name key=value>,这里使用这个方法就可以得到name。使用getAttributeName(),getAttributeValue(),可以得到<name key=value>中的key,value值。这里注意,getText()方法用于得到字符,不仅仅是<name key=value>xxxx</name>中的xxxx,如果解析的元素是纯字符的也通过这个方法得到。最后我们一般使用XmlPullParser中的START_DOCUMENT,END_DOCUMENT,START_TAG,END_TAG,TEXT等常量区分解析元素的类型。


(注意SAX使用的是SAXTransformerFactory进行写XML操作。DOM使用TransformerFactory进行写XML操作。SAX是基于流的操作,DOM是基于树结构的操作。两者的操作很相似,可以相互对照加强操作XML文件的类的掌握。)





        JAXP其实就是一些接口,包括SAX,DOM,XSLT,并定义了Source(DOMSource,SAXSource,StreamSource)与Result(DOMResult,SAXResult,StreamResult)接口进行输入输出,也就是说JAXP的使用上,就相当于SAX与DOM而已。因此并未予以采用。其实简单点说,就是JAXP就是DOM与SAX的集合而已,JAXP并未增加新方法或者功能,但是却可以使得SAX与DOM处理一些问题变得简单,JAXP本身就是API。(JAXP本身不提供任何的XML解析支持,同时依赖于解析器,但又不跟解析器耦合,因此可以任意切换解析器而无需修改源代码)


        JDOM与DOM相像,但是却有好些不同之处。JDOM与DOM都是很好内存的,超10M则溢出,这点就移动平台来说,耗内存是很麻烦的,但是操作的简便性很好。JDOM使用的也是DOM与SAX结合的方式,但是JDOM的DOMBuilder所得到的Document结构是不一样的,并且JDOM存在SAXBuilder,使用SAXBuilder得到Document对象。也就是说JDOM有DOMBuilder,SAXBuilder两种解析方式。同时注意JDOM本身也是融合了DOM的,解析的思想基本上就是DOM的。简单点说就是使用SAXBuilder实现Document进行解析xml文件。使用XMLOutputter进行进行xml文件的创建。



        DOM4J性能是最好的,但是可移植性不好。DOM4J读取XML文件有两种,分别是DOMReader与SAXReader,而写XML文件则是使用XMLWriter。同时使用的是将整个XML文件看成是一个Document对象进行操作,就像DOM一样。DOM4J需要下载操作所需的包。使用DocumentHelper进行文档创建。(DOM4J其实为解析XML文件提供了4个解析器,分别是SAXReader,DOMReader,XPPReader,XPP3Reader)(在创建Document上也有两个选择分别是DocumentFactory,DocumentHelper,使用createDocument()方法即可创建,其中DocumentHelper最为常见,也很好用)


        这里使用dom4j进行xml方面的文件操作,以减少资源消耗,增加运行效率,简化操作。


(文件操作的包装类是乱码的根源)

(未完成)

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
package com.hexiang.utils; import javax.xml.parsers.DocumentBuilder; import javax.xml.parsers.DocumentBuilderFactory; import org.w3c.dom.Document; import org.w3c.dom.Element; import org.w3c.dom.NodeList; /** * 本类是专门解析XML文件的,主要用于为系统读取自己的配置文件时提供最方便的解析操作 * @author HX * */ public class XmlManager { /** * 得到某节点下某个属性的值 * @param element 要获取属性的节点 * @param attributeName 要取值的属性名称 * @return 要获取的属性的值 * @author HX_2010-01-12 */ public static String getAttribute( Element element, String attributeName ) { return element.getAttribute( attributeName ); } /** * 获取指定节点下的文本 * @param element 要获取文本的节点 * @return 指定节点下的文本 * @author HX_2010-01-12 */ public static String getText( Element element ) { return element.getFirstChild().getNodeValue(); } /** * 解析某个xml文件,并在内存中创建DOM树 * @param xmlFile 要解析的XML文件 * @return 解析某个配置文件后的Document * @throws Exception xml文件不存在 */ public static Document parse( String xmlFile ) throws Exception { // 绑定XML文件,建造DOM树 DocumentBuilderFactory dbf = DocumentBuilderFactory.newInstance(); DocumentBuilder db = dbf.newDocumentBuilder(); Document domTree = db.parse( xmlFile ); return domTree; } /** * 获得某节点下的某个子节点(指定子节点名称,和某个属性的值) * 即获取parentElement下名字叫childName,并且属性attributeName的值为attributeValue的子结点 * @param parentElement 要获取子节点的那个父节点 * @param childName 要获取的子节点名称 * @param attributeName 要指定的属性名称 * @param attributeValue 要指定的属性的值 * @return 符合条件的子节点 * @throws Exception 子结点不存在或有多个符合条件的子节点 * @author HX_2008-12-01 */ public static Element getChildElement( Element parentElement, String childName, String attributeName, String attributeValue ) throws Exception { NodeList list = parentElement.getElementsByTagName( childName ); int count = 0; Element curElement = null; for ( int i = 0 ; i < list.getLength() ; i ++ ) { Element child = ( Element )list.item( i ); String value = child.getAttribute( attributeName ); if ( true == value.equals( attributeValue ) ) { curElement =
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值