android-XML解析之pull類型代碼解析

來源:互聯網
上載者:User

標籤:

    由於之前的項目使用過xml檔案的解析,但是在使用的時候都是從網上找到的代碼,稍作修改就使用了,然而對其中的原理並不知所以然,所以再次想使用的時候,感覺還是空空的,不知道如何下手,為了更加深入的理解xml檔案的解析,我從代碼實現的角度做一些理解,但是我在看代碼的時候,有些代碼的實現還是沒有辦法讀懂,還是太深奧。下面我就以我之見,寫一些東西,作為記錄。

    在android中XML的解析有三種,分別為:SAX(Simple API XML)、DOM(document object model)、以及今天我們要說的PULL類型,也是android官方提倡的使用方式。

    在講之前,我先寫出一般的使用方式,比如解析以下的XML文檔:


<?xml version="1.0" encoding="UTF-8"?><students>   <student id="1">      <name>cc</name>      <age>10</age>      <grade>100</grade>   </student>   <student id="2">      <name>cy</name>      <age>11</age>      <grade>89</grade>   <student></students>

一般的解析手段,java邏輯代碼如下(代碼截取與網路):

public class TestPullXml {    public List<Person> getPersons(InputStream instream) throws Exception {        List<Person> persons = null;        Person person = null;        XmlPullParser parser = Xml.newPullParser();//得到Pull解析器        parser.setInput(instream, "UTF-8");//設定下輸入資料流的編碼        int eventType = parser.getEventType();//得到第一個事件類型        while (eventType != XmlPullParser.END_DOCUMENT) {            //如果事件類型不是文檔結束的話則不斷處理事件            switch (eventType) {                case XmlPullParser.START_DOCUMENT://如果是文檔開始事件                    persons = new ArrayList<Person>();建立一個person集合                    break;                case (XmlPullParser.START_TAG)://如果遇到標籤開始                    String tagName = parser.getName();// 獲得解析器當前元素的名稱                    if ("person".equals(tagName)) {//如果當前標籤名稱是                           <person> person = new Person();//建立一個person                        //將元素的屬性值賦值給id                        person.setId(new Integer(parser.getAttributeValue(0)));                    }                    if (person != null) {//如果person已經建立完成                        if ("name".equals(tagName))//如果當前節點標記是name                            person.setName(new String(parser.nextText()));                        else if ("age".equals(tagName))//如果當前元素節點標記是age                            person.setAge(new Short(parser.nextText()));                    }                    break;                case (XmlPullParser.END_TAG)://如果遇到標籤結束                    if ("person".equals(parser.getName())) {//如果是person標籤結束                        persons.add(person);//將建立完成的person加入集合                        person = null;//並且置空                    }                    break;            }            eventType=parser.next();//進入下一個事件處理        }        return persons;    }

下面,我們對上述代碼,進行分行理解:


XmlPullParser parser = Xml.newPullParser();//得到Pull解析器
首先找到Xml類下的newPullParser方法:



/**  * Returns a new pull parser with namespace support.  */    public static XmlPullParser newPullParser() {        try {            KXmlParser parser = new KXmlParser();            parser.setFeature(XmlPullParser.FEATURE_PROCESS_DOCDECL, true);            parser.setFeature(XmlPullParser.FEATURE_PROCESS_NAMESPACES, true);            return parser;        } catch (XmlPullParserException e) {            throw new AssertionError();        }    }

通過上面的代碼,我們可以發現,實際上該函數返回了一個實現了XmlPullParser介面的類KXmlParser,並且給該對象設定了命名空間和文檔聲明,所以,對以後的parser對象,我們所需要分析的實現代碼,就要找KXmlParser這個類了。

parser.setInput(instream, "UTF-8");//設定下輸入資料流的編碼
這一步,我們先查看一下,官方文檔是怎麼解釋了:


Set the input source for parser to the given reader and resets the parser. The event type is set to the initial value START_DOCUMENT. Setting the reader to null will just stop parsing and reset parser state, allowing the parser to free internal resources such as parsing buffers.



相信大家可以理解這個方法的作用,但是我們還是看看它的實現代碼吧:


 //  public part starts here...    public void setInput(Reader reader) throws XmlPullParserException {        this.reader = reader;        line = 1;        column = 0;        type = START_DOCUMENT;        name = null;        namespace = null;        degenerated = false;        attributeCount = -1;        encoding = null;        version = null;        standalone = null;        if (reader == null)            return;        srcPos = 0;        srcCount = 0;        peekCount = 0;        depth = 0;        entityMap = new Hashtable<String, String>();        entityMap.put("amp", "&");        entityMap.put("apos", "‘");        entityMap.put("gt", ">");        entityMap.put("lt", "<");        entityMap.put("quot", "\"");    }

在這個方法中,初始化了很多在讀取XML過程中需要使用的成員變數,比如type,初始化為START_DOCUMENT,輸入資料流instream,這些都是解析時所必不可少的成員,所以在一開始,一定要調用該方法。設定輸入源。

int eventType = parser.getEventType();//得到第一個事件類型



首先我們要知道,XML的幾種事件類型:

START_DOCUMENT、START_TAG、TEXT、END_TAG、END_DOCUMENT
/******************************明天再寫**************************************/






android-XML解析之pull類型代碼解析

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.