什么是XML?
XML:extensiable markup language 被稱作可擴展標記語言
XML簡單的歷史介紹:
gml->sgml->html->xml
gml(通用標記語言)–在不同的機器進行通信的數據規范
sgml(標準通用標記語言)
html(超文本標記語言)
為什么我們需要使用XML呢?①我們沒有XML這種語言之前,我們使用的是String作為兩個程序之間的通訊!現在問題就來了,如果我們傳輸的是帶有關系型結構的數據,String怎么表達呢?String對關系型數據不擅長,要是描述起來也難免會有歧義的時候!關系型數據如圖下所示:
②HTML語言本身就有缺陷:
標記都是固定的,不能自定義。HTML語言中有什么標記就只能用什么標記
HTML標簽本身就缺少含義(tr標簽里面什么內容都能放進去,不規范!!)
HTML沒有實現真正的國際化
XML文件就解決了以上的問題了,如果使用XML描述上述圖片的關系,是非常簡單的!
<中國> <北京> <海淀>海淀> <豐臺>豐臺> 北京> <湖南> <長沙>長沙> <岳陽>岳陽> 湖南> <湖北> <武漢>武漢> <荊州>荊州> 湖北> 中國>
XML文件還能使用瀏覽器打開:
我們可以發現XML是可以描述很復雜的數據關系的
XML的用途①:配置文件(例子:Tomcat的web.xml,server.xml......),XML能夠非常清晰描述出程序之間的關系
②:程序間數據的傳輸,XML的格式是通用的,能夠減少交換數據時的復雜性!
③:充當小型數據庫,如果我們的數據有時候需要人工配置的,那么XML充當小型的數據庫是個不錯的選擇,程序直接讀取XML文件顯然要比讀取數據庫要快呢!
XML的技術架構XML被設計為“什么都不做”,XML數據或XML文檔只用于組織、存儲數據,除此之外的數據生成、讀取、傳送、存取等等操作都與XML本身無關!
于是乎,想要操作XML,就需要用到XML之外的技術了:
為XML定規則:現在一般使用DTD或Schema技術,當然了Schema技術更為先進!
解析XML的數據:一般使用DOM或者SAX技術,各有各的優點
提供樣式:XML一般用來存儲數據的,但設計者野心很大,也想用來顯示數據(但沒人用XML來顯示數據),就有了XSLT(eXtensiable Stylesheet Language Transformation)可擴展樣式轉換語言
XML語法: 文檔聲明:XML聲明放在XML的第一行
version----版本
encoding--編碼
standalone--獨立使用--默認是no。standalone表示該xml是不是獨立的,如果是yes,則表示這個XML文檔時獨立的,不能引用外部的DTD規范文件;如果是no,則該XML文檔不是獨立的,表示可以引用外部的DTD規范文檔。
正確的文檔聲明格式,屬性的位置不能改變!
元素
首先在這里說明一個概念:在XML中元素和標簽指的是同一個東西!不要被不同的名稱所迷惑了!
元素中需要值得注意的地方:
XML元素中的出現的空格和換行都會被當做元素內容進行處理
每個XML文檔必須有且只有一個根元素
元素必須閉合
大小寫敏感
不能交叉嵌套
不能以數字開頭
看起來好像有很多需要值得注意的地方,其實只需要記住:XML的語法是規范的!不要隨意亂寫!
屬性屬性是作為XML元素中的一部分的,命名規范也是和XML元素一樣的!
<中國 name="china"> 中國>注釋
注釋和HTML的注釋是一樣的
CDATA
在編寫XML文件時,有些內容可能不想讓解析引擎解析執行,而是當作原始內容處理。遇到此種情況,可以把這些內容放在CDATA區里,對于CDATA區域內的內容,XML解析程序不會處理,而是直接原封不動的輸出
語法:
轉義字符
對于一些單個字符,若想顯示其原始樣式,也可以使用轉義的形式予以處理。
處理指令處理指令,簡稱PI (processing instruction)。處理指令用來指揮解析引擎如何解析XML文檔內容。
例如:
在XML文檔中可以使用xml-stylesheet指令,通知XML解析引擎,應用css文件顯示xml文檔內容。
XML代碼:
廣州 深圳
CSS代碼:
guangzhou{ font-size: 40px; }
效果:
JDK中的XML API①:JAXP(The Java API For XML Processing):主要負責解析XML
②:JAXB(Java Architecture for XML Binding):主要負責將XML映射為Java對象
什么是XML解析前面XML章節已經說了,XML被設計為“什么都不做”,XML只用于組織、存儲數據,除此之外的數據生成、讀取、傳送等等的操作都與XML本身無關!
XML解析就是讀取XML的數據!
XML解析方式XML解析方式分為兩種:
①:dom(Document Object Model)文檔對象模型,是W3C組織推薦解析XML的一種方式
②:sax(Simple API For XML),它是XML社區的標準,幾乎所有XML解析器都支持它!
XML解析操作從上面的圖很容易發現,應用程序不是直接對XML文檔進行操作的,而是由XML解析器對XML文檔進行分析,然后應用程序通過XML解析器所提供的DOM接口或者SAX接口對分析結果進行操作,從而間接地實現了對XML文檔的訪問!
常用的解析器和解析開發包的關系如下所示:
為什么有3種開發包?jaxp開發包是JDK自帶的,不需要導入開發包。
由于sun公司的jaxp不夠完善,于是就被研發了Jdom。XML解析如果使用Jdom,需要導入開發包
dom4j是由于Jdom的開發人員出現了分歧,dom4j由Jdom的一批開發人員所研發。XML解析如果使用Jdom,需要導入開發包【現在用dom4j是最多的!】
jaxp雖然jaxp解析XML的性能以及開發的簡易度是沒有dom4j好,但是jaxp不管怎么說都是JDK內置的開發包,我們是需要學習的!
DOM解析操作DOM解析是一個基于對象的API,它把XML的內容加載到內存中,生成與XML文檔內容對應的模型!當解析完成,內存中會生成與XML文檔的結構與之對應的DOM對象樹,這樣就能夠根據樹的結構,以節點的形式對文檔進行操作!
簡單來說:DOM解析會把XML文檔加載到內存中,生成DOM樹的元素都是以對象的形式存在的!我們操作這些對象就能夠操作XML文檔了!
下面這樣圖就能很好地說明了,是怎么樣生成與XML文檔內容對應的DOM樹!
既然XML文檔的數據是帶有關系型的,那么生成的DOM樹的節點也是有關系的:
位于一個節點之上的節點是該節點的父節點(parent)
一個節點之下的節點是該節點的子節點(children)
同一層次,具有相同父節點的節點是兄弟節點(sibling)
一個節點的下一個層次的節點集合是節點后代(descendant)
父、祖父節點及所有位于節點上面的,都是節點的祖先(ancestor)
在DOM解析中有幾個核心的操作接口:
Document【代表整個XML文檔,通過Document節點可以訪問XML文件中所有的元素內容!】
Node【Node節點幾乎在XML操作接口中幾乎相當于普通Java類的Object,很多核心接口都實現了它,在下面的關系圖可以看出!】
NodeList【代表著一個節點的集合,通常是一個節點中子節點的集合!】
NameNodeMap【表示一組節點和其唯一名稱對應的一一對應關系,主要用于屬性節點的表示(書上說是核心的操作接口,但我好像沒用到!呃呃呃,等我用到了,我再來填坑!)】
節點之間的關系圖:
有人可能會很難理解,為什么Document接口比Node接口還小,呃呃呃,我是這樣想的:一個Document由無數個Node組成,這樣我也能把Document當成是Node呀!如果實在想不通:人家都這樣設計了,你有種就不用啊!!(開玩笑的.....)
好的,不跟你們多bb,我們來使用一下Dom的方式解析XML文檔吧!
XML文檔代碼
廣州 深圳 北京 上海
根據XML解析的流程圖,我們先要獲取到解析器對象!
public class DomParse { public static void main(String[] args) throws ParserConfigurationException, IOException, SAXException { //API規范:需要用一個工廠來造解析器對象,于是我先造了一個工廠! DocumentBuilderFactory documentBuilderFactory = DocumentBuilderFactory.newInstance(); //獲取解析器對象 DocumentBuilder documentBuilder = documentBuilderFactory.newDocumentBuilder(); //獲取到解析XML文檔的流對象 InputStream inputStream = DomParse.class.getClassLoader().getResourceAsStream("city.xml"); //解析XML文檔,得到了代表XML文檔的Document對象! Document document = documentBuilder.parse(inputStream); } }
解析XML文檔的內容用來干嘛?無非就是增刪改查遍歷,只要我們會對XML進行增刪改查,那就說明我們是會使用DOM解析的!
遍歷我們再來看一下XML文檔的內容,如果我們要遍歷該怎么做?:
可能我們會有兩種想法:
①:從XML文檔內容的上往下看,看到什么就輸出什么!【這正是SAX解析的做法】
②:把XML文檔的內容分成兩部分,一部分是有子節點的,一部分是沒有子節點的(也就是元素節點!)。首先我們判斷是否為元素節點,如果是元素節點就輸出,不是元素節點就獲取到子節點的集合,再判斷子節點集合中的是否是元素節點,如果是元素節點就輸出,如果不是元素節點獲取到該子節點的集合....好的,一不小心就遞歸了...
我們來對XML文檔遍歷一下吧,為了更好地重用,就將它寫成一個方法吧(也是能夠更好地用遞歸實現功能)!
public class DomParse { public static void main(String[] args) throws ParserConfigurationException, IOException, SAXException { //API規范:需要用一個工廠來造解析器對象,于是我先造了一個工廠! DocumentBuilderFactory documentBuilderFactory = DocumentBuilderFactory.newInstance(); //獲取解析器對象 DocumentBuilder documentBuilder = documentBuilderFactory.newDocumentBuilder(); //獲取到解析XML文檔的File對象 InputStream inputStream = DomParse.class.getClassLoader().getResourceAsStream("city.xml"); //解析XML文檔,得到了代表XML文檔的Document對象! Document document = documentBuilder.parse(inputStream); //把代表XML文檔的document對象傳遞進去給list方法 list(document); } //我們這里就接收Node類型的實例對象吧!多態!!! private static void list(Node node) { //判斷是否是元素節點,如果是元素節點就直接輸出 if (node.getNodeType() == Node.ELEMENT_NODE) { System.out.println(node.getNodeName()); } //....如果沒有進入if語句,下面的肯定就不是元素節點了,所以獲取到子節點集合 NodeList nodeList = node.getChildNodes(); //遍歷子節點集合 for (int i = 0; i < nodeList.getLength(); i++) { //獲取到其中的一個子節點 Node child = nodeList.item(i); //...判斷該子節點是否為元素節點,如果是元素節點就輸出,不是元素節點就再獲取到它的子節點集合...遞歸了 list(child); } } }
效果:
查詢現在我要做的就是:讀取guangzhou這個節點的文本內容!
private static void read(Document document) { //獲取到所有名稱為guangzhou節點 NodeList nodeList = document.getElementsByTagName("guangzhou"); //取出第一個名稱為guangzhou的節點 Node node = nodeList.item(0); //獲取到節點的文本內容 String value = node.getTextContent(); System.out.println(value); }
效果:
增加現在我想多增加一個城市節點(杭州),我需要這樣做:
private static void add(Document document) { //創建需要增加的節點 Element element = document.createElement("hangzhou"); //向節點添加文本內容 element.setTextContent("杭州"); //得到需要添加節點的父節點 Node parent = document.getElementsByTagName("china").item(0); //把需要增加的節點掛在父節點下面去 parent.appendChild(element); }
做到這里,我僅僅在內存的Dom樹下添加了一個節點,要想把內存中的Dom樹寫到硬盤文件中,需要轉換器!
獲取轉換器也十分簡單:
//獲取一個轉換器它需要工廠來造,那么我就造一個工廠 TransformerFactory transformerFactory = TransformerFactory.newInstance(); //獲取轉換器對象 Transformer transformer = transformerFactory.newTransformer();
把內存中的Dom樹更新到硬盤文件中的transform()方法就稍稍有些復雜了!
它需要一個Source實例對象和Result的實例對象,這兩個接口到底是什么玩意啊?
于是乎,我就去查API,發現DomSource實現了Source接口,我們使用的不正是Dom解析嗎,再看看構造方法,感覺就是它了!
而SteamResult實現了Result接口,有人也會想,DomResult也實現了Result接口啊,為什么不用DomResult呢?我們現在做的是把內存中的Dom樹更新到硬盤文件中呀,當然用的是StreamResult啦!
完整代碼如下:
private static void add(Document document) throws TransformerException { //創建需要增加的節點 Element element = document.createElement("hangzhou"); //向節點添加文本內容 element.setTextContent("杭州"); //得到需要添加節點的父節點 Node parent = document.getElementsByTagName("china").item(0); //把需要增加的節點掛在父節點下面去 parent.appendChild(element); //獲取一個轉換器它需要工廠來造,那么我就造一個工廠 TransformerFactory transformerFactory = TransformerFactory.newInstance(); //獲取轉換器對象 Transformer transformer = transformerFactory.newTransformer(); //把內存中的Dom樹更新到硬盤中 transformer.transform(new DOMSource(document),new StreamResult("city.xml")); }
效果:
剛剛增加的節點是在china節點的末尾處的,現在我想指定增加節點的在beijing節點之前,是這樣做的:
private static void add2(Document document) throws TransformerException { //獲取到beijing節點 Node beijing = document.getElementsByTagName("beijing").item(0); //創建新的節點 Element element = document.createElement("guangxi"); //設置節點的文本內容 element.setTextContent("廣西"); //獲取到要創建節點的父節點, Node parent = document.getElementsByTagName("china").item(0); //將guangxi節點插入到beijing節點之前! parent.insertBefore(element, beijing); //將內存中的Dom樹更新到硬盤文件中 TransformerFactory transformerFactory = TransformerFactory.newInstance(); Transformer transformer = transformerFactory.newTransformer(); transformer.transform(new DOMSource(document), new StreamResult("city.xml")); }
效果:
刪除現在我要刪除的是beijing這個節點!
private static void delete(Document document) throws TransformerException { //獲取到beijing這個節點 Node node = document.getElementsByTagName("beijing").item(0); //獲取到父節點,然后通過父節點把自己刪除了 node.getParentNode().removeChild(node); //把內存中的Dom樹更新到硬盤文件中 TransformerFactory transformerFactory = TransformerFactory.newInstance(); Transformer transformer = transformerFactory.newTransformer(); transformer.transform(new DOMSource(document), new StreamResult("city.xml")); }
效果:
修改將guangzhou節點的文本內容修改成廣州你好
private static void update(Document document) throws TransformerException { //獲取到guangzhou節點 Node node = document.getElementsByTagName("guangzhou").item(0); node.setTextContent("廣州你好"); //將內存中的Dom樹更新到硬盤文件中 TransformerFactory transformerFactory = TransformerFactory.newInstance(); Transformer transformer = transformerFactory.newTransformer(); transformer.transform(new DOMSource(document), new StreamResult("city.xml")); }
效果:
操作屬性XML文檔是可能帶有屬性值的,現在我們要guangzhou節點上的屬性
private static void updateAttribute(Document document) throws TransformerException { //獲取到guangzhou節點 Node node = document.getElementsByTagName("guangzhou").item(0); //現在node節點沒有增加屬性的方法,所以我就要找它的子類---Element Element guangzhou = (Element) node; //設置一個屬性,如果存在則修改,不存在則創建! guangzhou.setAttribute("play", "gzchanglong"); //如果要刪除屬性就用removeAttribute()方法 //將內存中的Dom樹更新到硬盤文件中 TransformerFactory transformerFactory = TransformerFactory.newInstance(); Transformer transformer = transformerFactory.newTransformer(); transformer.transform(new DOMSource(document), new StreamResult("city.xml")); }
效果:
SAX解析SAX采用的是一種順序的模式進行訪問,是一種快速讀取XML數據的方式。當時候SAX解析器進行操作時,會觸發一系列事件SAX。采用事件處理的方式解析XML文件,利用 SAX 解析 XML 文檔,涉及兩個部分:解析器和事件處理器
sax是一種推式的機制,你創建一個sax 解析器,解析器在發現xml文檔中的內容時就告訴你(把事件推給你). 如何處理這些內容,由程序員自己決定。
當解析器解析到聲明頭時,會觸發事件。解析到
首先我們還是先拿到SAX的解析器再說吧!
//要得到解析器對象就需要造一個工廠,于是我造了一個工廠 SAXParserFactory saxParserFactory = SAXParserFactory.newInstance(); //獲取到解析器對象 SAXParser saxParse = saxParserFactory.newSAXParser();
調用解析對象的解析方法的時候,需要的不僅僅是XML文檔的路徑!還需要一個事件處理器!
事件處理器都是由我們程序員來編寫的,它一般繼承DefaultHandler類,重寫如下5個方法:
@Override public void startDocument() throws SAXException { super.startDocument(); } @Override public void endDocument() throws SAXException { super.endDocument(); } @Override public void startElement(String uri, String localName, String qName, Attributes attributes) throws SAXException { super.startElement(uri, localName, qName, attributes); } @Override public void endElement(String uri, String localName, String qName) throws SAXException { super.endElement(uri, localName, qName); } @Override public void characters(char[] ch, int start, int length) throws SAXException { super.characters(ch, start, length); }
獲取解析器,調用解析器解析XML文檔的代碼:
public static void main(String[] args) throws Exception{ //要得到解析器對象就需要造一個工廠,于是我造了一個工廠 SAXParserFactory saxParserFactory = SAXParserFactory.newInstance(); //獲取到解析器對象 SAXParser saxParse = saxParserFactory.newSAXParser(); //獲取到XML文檔的流對象 InputStream inputStream = SAXParse.class.getClassLoader().getResourceAsStream("city.xml"); saxParse.parse(inputStream, new MyHandler()); }
事件處理器的代碼:
public class MyHandler extends DefaultHandler { @Override public void startDocument() throws SAXException { System.out.println("我開始來掃描啦!!!!"); } @Override public void endDocument() throws SAXException { System.out.println("我結束了!!!!"); } @Override public void startElement(String uri, String localName, String qName, Attributes attributes) throws SAXException { //如果要解析出節點屬性的內容,也非常簡單,只要通過attributes變量就行了! //輸出節點的名字! System.out.println(qName); } @Override public void endElement(String uri, String localName, String qName) throws SAXException { System.out.println(qName); } @Override public void characters(char[] ch, int start, int length) throws SAXException { System.out.println(new String(ch,start,length)); } }
我們發現,事件處理器的代碼都非常簡單,然后就如此簡單地就能夠遍歷整個XML文檔了!
如果要查詢多帶帶的某個節點的內容也是非常簡單的喲!只要在startElement()方法中判斷名字是否相同即可!
現在我只想查詢guangzhou節點的內容:
//定義一個標識量,用于指定查詢某個節點的內容 boolean flag = false; @Override public void startElement(String uri, String localName, String qName, Attributes attributes) throws SAXException { //如果節點名稱是guangzhou,我才輸出,并且把標識量設置為true if (qName == "guangzhou") { System.out.println(qName); flag = true; } } @Override public void characters(char[] ch, int start, int length) throws SAXException { //只有在flag為true的情況下我才輸出文本的內容 if (flag == true) { System.out.println(new String(ch, start, length)); } } @Override public void endElement(String uri, String localName, String qName) throws SAXException { //在執行到元素的末尾時,不要忘了將標識量改成false if (qName == "guangzhou" && flag == true) { System.out.println(qName); flag = false; } }
效果:
DOM和SAX解析的區別:DOM解析讀取整個XML文檔,在內存中形成DOM樹,很方便地對XML文檔的內容進行增刪改。但如果XML文檔的內容過大,那么就會導致內存溢出!
SAX解析采用部分讀取的方式,可以處理大型文件,但只能對文件按順序從頭到尾解析一遍,不支持文件的增刪改操作
DOM和SAX解析有著明顯的差別,什么時候使用DOM或者SAX就非常明了了。
dom4jDom4j是一個非常優秀的Java XML API,具有性能優異、功能強大和極易使用的特點。
為什么需要有dom4jdom缺點:比較耗費內存
sax缺點:只能對xml文件進行讀取,不能修改,添加,刪除
dom4j:既可以提高效率,同時也可以進行crud操作
因為dom4j不是sun公司的產品,所以我們開發dom4j需要導入開發包
獲取dom4j的解析器使用dom4j對XML文檔進行增刪改查,都需要獲取到dom4j的解析器
//獲取到解析器 SAXReader saxReader = new SAXReader(); //獲取到XML文件的流對象 InputStream inputStream = DOM4j.class.getClassLoader().getResourceAsStream("1.xml"); //通過解析器讀取XML文件 Document document = saxReader.read(inputStream);獲取Document對象
我們都知道,Document代表的是XML文檔,一般我們都是通過Document對象開始,來進行CRUD(增刪改查)操作的!
獲取Document對象有三種方式:
①:讀取XML文件,獲得document對象(這種最常用)
SAXReader reader = new SAXReader(); Document document = reader.read(new File("input.xml"));
②:解析XML形式的文本,得到document對象
String text = ""; Document document=DocumentHelper.parseText(text);
③:主動創建document對象.
Document document =DocumentHelper.createDocument(); //創建根節點 Element root = document.addElement("members");CRUD的重要一句話:
讀取XML文檔的數據,都是通過Document獲取根元素,再通過根元素獲取得到其他節點的,從而進行操作!
如果XML的結構有多層,需要一層一層地獲取!
查詢@Test public void read() throws DocumentException { //獲取到解析器 SAXReader saxReader = new SAXReader(); //獲取到XML文件的流對象 InputStream inputStream = dom4j11.class.getClassLoader().getResourceAsStream("1.xml"); //通過解析器讀取XML文件 Document document = saxReader.read(inputStream); //獲取得到根節點 Element root = document.getRootElement(); //獲取得到name節點 Element name = root.element("name"); //得到了name節點,就可以獲取name節點的屬性或者文本內容了! String text = name.getText(); String attribute = name.attributeValue("littleName"); System.out.println("文本內容是:" + text); System.out.println("屬性內容是:" + attribute); }
XML文件如下:
zhongfucheng 20
效果:
多層結構的查詢:
//獲取得到根節點 Element root = document.getRootElement(); //一層一層地獲取到節點 Element element = root.element("guangdong").element("guangzhou").element("luogang"); String value = element.getText(); System.out.println(value);
XML文件和結果:
增加在DOM4j中要對內存中的DOM樹寫到硬盤文件中,也是要有轉換器的支持的!
dom4j提供了XMLWriter供我們對XML文檔進行更新操作,一般地創建XMLWriter的時候我們都會給出兩個參數,一個是Writer,一個是OutputFormat
這個OutputFormat有什么用的呢?其實就是指定回寫XML的格式和編碼格式。細心的朋友會發現,上面我們在jaxp包下使用dom解析的Transformer類,把內存中的DOM樹更新到文件硬盤中,是沒有格式的!不信倒回去看看!這個OutputFormat就可以讓我們更新XML文檔時也能帶有格式!
//創建帶有格式的對象 OutputFormat outputFormat = OutputFormat.createPrettyPrint(); //設置編碼,默認的編碼是gb2312,讀寫的編碼不一致,會導致亂碼的! outputFormat.setEncoding("UTF-8"); //創建XMLWriter對象 XMLWriter xmlWriter = new XMLWriter(new FileWriter("2.xml"), outputFormat); //XMLWriter對象寫入的是document xmlWriter.write(document); //關閉流 xmlWriter.close();
下面我們就為在person節點下新創建一個name節點吧,完整的代碼如下:!
@Test public void add() throws Exception { //獲取到解析器 SAXReader saxReader = new SAXReader(); //獲取到XML文件的流對象 InputStream inputStream = dom4j11.class.getClassLoader().getResourceAsStream("1.xml"); //通過解析器讀取XML文件 Document document = saxReader.read(inputStream); //創建出新的節點,為節點設置文本內容 Element newElement = DocumentHelper.createElement("name"); newElement.setText("ouzicheng"); //獲取到根元素 Element root = document.getRootElement(); //把新創建的name節點掛在根節點下面 root.add(newElement); //創建帶有格式的對象 OutputFormat outputFormat = OutputFormat.createPrettyPrint(); //設置編碼,默認的編碼是gb2312,讀寫的編碼不一致,會導致亂碼的! outputFormat.setEncoding("UTF-8"); //創建XMLWriter對象 XMLWriter xmlWriter = new XMLWriter(new FileWriter("2.xml"), outputFormat); //XMLWriter對象寫入的是document xmlWriter.write(document); //關閉流 xmlWriter.close(); }
效果如下,是有格式的!
在指定的位置增加節點!現在我想的就是在age屬性前面添加節點!
//創建一個新節點 Element element = DocumentHelper.createElement("name"); element.setText("ouzciheng"); //獲取得到person下所有的節點元素! List list = document.getRootElement().elements(); //將節點添加到指定的位置上 list.add(1, element);
效果圖:
修改XMLWriter和獲取Document對象的代碼我就不貼出來了,反正都是一樣的了!
//獲取得到age元素 Element age = document.getRootElement().element("age"); age.setText("9999");
效果如下:
刪除XMLWriter和獲取Document對象的代碼我就不貼出來了,反正都是一樣的了!
//獲取得到age節點 Element age = document.getRootElement().element("age"); //得到age節點的父節點,使用父節點的remove刪除age節點! age.getParent().remove(age);
效果:
XPATH 什么是XPATHXPath 是一門在 XML 文檔中查找信息的語言。XPath 用于在 XML 文檔中通過元素和屬性進行導航。為什么我們需要用到XPATH
上面我們使用dom4j的時候,要獲取某個節點,都是通過根節點開始,一層一層地往下尋找,這就有些麻煩了!
如果我們用到了XPATH這門語言,要獲取得到XML的節點,就非常地方便了!
快速入門使用XPATH需要導入開發包jaxen-1.1-beta-7,我們來看官方的文檔來入門吧。
XPATH的文檔非常國際化啊,連中文都有
XPATH文檔中有非常多的實例,非常好學,對著來看就知道了!
我們來用XPATH技術讀取XML文件的信息吧,XML文檔如下:
之前,我們是先獲取根節點,再獲取guangdong節點再獲取guangzhou節點,然后才能讀取tianhe節點或者luogang節點的,下面我們來看一下使用XPATH可以怎么的便捷!
//直接獲取到luogang節點 org.dom4j.Node node = document.selectSingleNode("http://luogang"); //獲取節點的內容 String value = node.getText(); System.out.println(value);
效果:
獲取什么類型的節點,XPATH的字符串應該怎么匹配,查文檔就知道了,這里就不再贅述了。!
如果文章有錯的地方歡迎指正,大家互相交流。習慣在微信看技術文章的同學,可以關注微信公眾號:Java3y
文章版權歸作者所有,未經允許請勿轉載,若此文章存在違規行為,您可以聯系管理員刪除。
轉載請注明本文地址:http://specialneedsforspecialkids.com/yun/70977.html
摘要:什么是簡單的說就是一個運行的網絡服務器,底層是的一個程序,它也是和的一個容器。在瀏覽器地址欄輸入如果能夠出現頁面,說明配置成功了注意如果在使用時出現了很大原因就是和的版本不匹配。 什么是Tomcat Tomcat簡單的說就是一個運行JAVA的網絡服務器,底層是Socket的一個程序,它也是JSP和Serlvet的一個容器。 為什么我們需要用到Tomcat 如果你學過html,css,...
摘要:軟件項目的管理就會變得簡單很多。比如說的驅動程序,,在是獲取不到的,就需要手工上傳到里是倉庫組,在里沒有這個概念,是特有的。 什么是Maven Maven是一個采用純Java編寫的開源項目管理工具, Maven采用了一種被稱之為Project Object Model (POM)概念來管理項目,所有的項目配置信息都被定義在一個叫做POM.xml的文件中.. Maven是一款跨平臺的項目...
摘要:前言由于寫的文章已經是有點多了,為了自己和大家的檢索方便,于是我就做了這么一個博客導航。 前言 由于寫的文章已經是有點多了,為了自己和大家的檢索方便,于是我就做了這么一個博客導航。 由于更新比較頻繁,因此隔一段時間才會更新目錄導航哦~想要獲取最新原創的技術文章歡迎關注我的公眾號:Java3y Java3y文章目錄導航 Java基礎 泛型就這么簡單 注解就這么簡單 Druid數據庫連接池...
摘要:前言在的第二篇中主要講解了模塊的使用容器創建對象的問題,模塊主要是解決對象的創建和對象之間的依賴關系,因此本博文主要講解如何使用容器來解決對象之間的依賴關系回顧以前對象依賴我們來看一下我們以前關于對象依賴,是怎么的歷程直接對象在最開始,我們 前言 在Spring的第二篇中主要講解了Spring Core模塊的使用IOC容器創建對象的問題,Spring Core模塊主要是解決對象的創建和...
摘要:是一種特殊的增強切面切面由切點和增強通知組成,它既包括了橫切邏輯的定義也包括了連接點的定義。實際上,一個的實現被拆分到多個類中在中聲明切面我們知道注解很方便,但是,要想使用注解的方式使用就必須要有源碼因為我們要 前言 只有光頭才能變強 上一篇已經講解了Spring IOC知識點一網打盡!,這篇主要是講解Spring的AOP模塊~ 之前我已經寫過一篇關于AOP的文章了,那篇把比較重要的知...
閱讀 2436·2019-08-30 15:52
閱讀 2237·2019-08-30 12:51
閱讀 2833·2019-08-29 18:41
閱讀 2812·2019-08-29 17:04
閱讀 811·2019-08-29 15:11
閱讀 1720·2019-08-28 18:02
閱讀 3603·2019-08-26 10:22
閱讀 2510·2019-08-26 10:12