[Android] android平臺下sax,dom,pull解析方式性能比較

1.Android中三種XML的解析方式,分別爲Dom,Sax,Pull,其中Pull的解析方式最優java

2.Dom,Sax,Pull解析方式的區別node

(1).Dom解析方式:ide

首先一會兒加載整個文檔而後再挨個節點解析,費流量性能

優勢:對於處理大文檔,以及能力強的CPU性能比較快fetch

缺點:對於處理能力不夠強的CPU一會兒可能受不了,就像一我的一口先吃下一個大西瓜,再來嚼.ui

(2).Sax解析方式:url

SAX是事件驅動型解析方式spa

雖然說是事件驅動型的和PULL差很少,但沒有像pull那樣提供next接口,想向下繼續解析就向下,沒有靈活性,死板,包括獲得數據也是用模板弄好,對於特殊的數據組裝還要用變量控制。調試

sax是選擇性的解析,他是解析符合條件的內容。code

手動中止:
解析完須要的東西后就拋異常吧,好比throw new SAXException("已拿到數據,中斷解析!!!");

(3).Pull的解析方式:

Pull驅動型解析方式,加載時不把全部的節點都加載到解析機裏,只是去一個一個節點去查找,若是是一個節點並且須要這個節點就取出來,不像DOM,無論你要不要都放在解析機裏,要拿就拿,不拿就算了.,減小流量的使用

3.綜上以爲Pull解析方式最優,經過調試代碼發現,解析同一個XML文件,pull解析方式花的時間最少.

核心代碼以下:

//DOM解析方式

private List<River> fetchRiverFromXmlByDom(String fileName) {

    long startTime = System.currentTimeMillis();

    List<River> rivers = new ArrayList<River>();

    // 加載xml文檔的工廠

    DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance();

    InputStream inputStream = null;

    try {

        DocumentBuilder builder = factory.newDocumentBuilder();

        // 加入文件流

        inputStream = getAssets().open(fileName);

        // 轉化爲decument文檔對象

        Document document = builder.parse(inputStream);

        // 得到最根節點

        Element root = document.getDocumentElement();

        // 經過tag得到全部根節點下面的節點

        NodeList nodeList = root.getElementsByTagName(riverStr);

        // 獲得根節點下面有多少個節點

        int noteListSize = nodeList.getLength();

        // 聲明river對象,river類中包含全部的節點string

        River river = null;

        for (int i = 0; i < noteListSize; i++) {

            river = new River();

            // 得到節點元素

            Element element = (Element) nodeList.item(i);

            // 設置經過屬性名獲得的節點元素

            river.setName(element.getAttribute(nameStr));

            river.setLength(Integer.parseInt(element.getAttribute(lengthStr)));

            // 經過tag名獲得全部節點,再取得第一個節點(由於只有一個節點,若是這裏面還有節點得再來一個相似的循環)

            Element introTag = (Element) element.getElementsByTagName(introductionStr).item(0);

            river.setIntroduction(introTag.getFirstChild().getNodeValue());

            Element imageUrlTag = (Element) element.getElementsByTagName(imageurlStr).item(0);

            river.setImageurl(imageUrlTag.getFirstChild().getNodeValue());

            // 收集全部的節點到這個集合裏

            rivers.add(river);

        }

    } catch (ParserConfigurationException e) {

        e.printStackTrace();

    } catch (IOException e) {

        e.printStackTrace();

    } catch (SAXException e) {

        e.printStackTrace();

    }

    Log.d(T, "exec fetchRiverFromXmlByDom use time = "

            + (System.currentTimeMillis() - startTime));

    return rivers;

}

SAX解析方式:

private List<River> fetchRiverFormXmlBySAX(String fileName) {

    long startTime = System.currentTimeMillis();

    List<River> rivers = null;

    SAXParserFactory factory = SAXParserFactory.newInstance();

    InputStream inputStream = null;

    try {

        //獲得解析機

        SAXParser parser = factory.newSAXParser();

        //讀取數據

        XMLReader reader = parser.getXMLReader();

        //取數據的句柄

        MySaxHandler handler = new MySaxHandler();

        reader.setContentHandler(handler);

        inputStream = getAssets().open(fileName);

        reader.parse(new InputSource(inputStream));

        rivers = handler.getRivers();

    } catch (ParserConfigurationException e) {

        e.printStackTrace();

    } catch (SAXException e) {

        e.printStackTrace();

    } catch (IOException e) {

        e.printStackTrace();

    }

    Log.d(T, "exec fetchRiverFormXmlBySAX use time = "

            + (System.currentTimeMillis() - startTime));

    return rivers;

}



private class MySaxHandler extends DefaultHandler {



    private List<River> rivers = null;



    private boolean isRiver = false;



    private boolean isIntrocduce = false;



    private boolean isImageUrl = false;



    private River river = null;



    private String TAG = "MySaxHandler";



    public MySaxHandler() {

        rivers = new ArrayList<River>();

    }



    @Override

    public void startDocument() throws SAXException {

        super.startDocument();

        Log.d(TAG, "### startDocument");

    }



    @Override

    public void endDocument() throws SAXException {

        super.endDocument();

        Log.d(TAG, "### endDocument");

    }



    @Override

    public void startElement(String uri, String localName, String qName,

            Attributes attributes) throws SAXException {

        super.startElement(uri, localName, qName, attributes);

        String tagName = localName.length() > 0 ? localName : qName;

        if (tagName.equals(riverStr)) {

            isRiver = true;

            river = new River();

            river.setName(attributes.getValue(nameStr));

            river.setLength(Integer.parseInt(attributes.getValue(lengthStr)));

        }

        if (isRiver) {

            if (tagName.equals(introductionStr)) {

                isIntrocduce = true;

            } else if (tagName.equals(imageurlStr)) {

                isImageUrl = true;

            }

        }



    }



    @Override

    public void endElement(String uri, String localName, String qName)

            throws SAXException {

        super.endElement(uri, localName, qName);

        // Log.d(TAG, "### endElement uri=" + uri + " localName=" +

        // localName + " qName=" + qName);

        String tagName = localName.length() != 0 ? localName : qName;

        if (tagName.equals(riverStr)) {

            isRiver = false;

            rivers.add(river);

        }

        if (isRiver) {

            if (tagName.equals(introductionStr)) {

                isIntrocduce = false;

            } else if (tagName.equals(imageurlStr)) {

                isImageUrl = false;

            }

        }

    }



    @Override

    public void characters(char[] ch, int start, int length)

            throws SAXException {

        super.characters(ch, start, length);

        if (isIntrocduce) {

            river.setIntroduction(river.getIntroduction() == null ? "" : river

                    .getIntroduction() + new String(ch, start, length));

        } else if (isImageUrl) {

            river.setImageurl(river.getImageurl() == null ? "" : river.getImageurl()

                    + new String(ch, start, length));

        }

    }



    public List<River> getRivers() {

        return rivers;

    }



}

Pull解析方式:

private List<River> fetchRiverFormXmlByPull(String fileName) {

    long startTime = System.currentTimeMillis();

    List<River> rivers = new ArrayList<River>();

    River river = null;

    InputStream inputStream = null;

    // 得到解析機對象

    XmlPullParser xmlPullParser = Xml.newPullParser();

    try {

        // 獲得文件流

        inputStream = getAssets().open(fileName);

        xmlPullParser.setInput(inputStream, "utf-8");

        // 得到命名空間(必須調用,不然會拋出異常)

        xmlPullParser.setFeature(XmlPullParser.FEATURE_PROCESS_NAMESPACES, false);

        // Returns the type of the current event (START_TAG, END_TAG, TEXT,

        // etc.)

        int eventType = xmlPullParser.getEventType();

        while (eventType != XmlPullParser.END_DOCUMENT) {

            switch (eventType) {

                //開始節點<xxx>

                case XmlPullParser.START_TAG:

                    String tag = xmlPullParser.getName();

                    //Log.d(T, "START_TAG:" + tag);

                    if (tag.equalsIgnoreCase(riverStr)) {

                        river = new River();

                        river.setName(xmlPullParser.getAttributeValue(null, nameStr));

                        river.setLength(Integer.parseInt(xmlPullParser.getAttributeValue(null,

                                lengthStr)));

                    } else if (river != null) {

                        if (tag.equalsIgnoreCase(introductionStr)) {

                            river.setIntroduction(xmlPullParser.nextText());

                        } else if (tag.equalsIgnoreCase(imageurlStr)) {

                            river.setImageurl(xmlPullParser.nextText());

                        }

                    }

                    break;

                    //結束節點</xx>

                case XmlPullParser.END_TAG:

                    //Log.d(T, "END_TAG:" + xmlPullParser.getName());

                    if (xmlPullParser.getName().equalsIgnoreCase(riverStr) && river != null) {

                        rivers.add(river);

                        river = null;

                    }

                    break;

                default:

                    break;

            }

            eventType = xmlPullParser.next();

        }

    } catch (XmlPullParserException e) {

        e.printStackTrace();

    } catch (IOException e) {

        e.printStackTrace();

    }

    Log.d(T, "exec fetchRiverFormXmlByPull use time = "

            + (System.currentTimeMillis() - startTime));

    return rivers;

}
相關文章
相關標籤/搜索