欧美bbbwbbbw肥妇,免费乱码人妻系列日韩,一级黄片

淺談Android Studio 解析XML的三種方法

 更新時(shí)間:2018年07月31日 09:41:22   作者:天一方藍(lán)  
這篇文章主要介紹了淺談Android Studio 解析XML的三種方法,Android Studio 解析XML常見(jiàn)的三種方式:DOM PULL SAX,非常具有實(shí)用價(jià)值,需要的朋友可以參考下

一丶概述

文件解析要求,json解析和xml解析,前面文章說(shuō)過(guò)Json轉(zhuǎn)實(shí)體類(lèi),這里就說(shuō)說(shuō)解析XML

內(nèi)容:

Android Studio 解析XML常見(jiàn)的三種方式:DOM PULL SAX (實(shí)現(xiàn)XML轉(zhuǎn)實(shí)體類(lèi)并打印輸出)

效果演示:


二丶正文

SAX(Simple API for XML) 使用流式處理的方式,它并不記錄所讀內(nèi)容的相關(guān)信息。它是一種以事件為驅(qū)動(dòng)的XML API,解析速度快,占用內(nèi)存少。使用回調(diào)函數(shù)來(lái)實(shí)現(xiàn)。 缺點(diǎn)是不能倒退。

DOM(Document Object Model) 是一種用于XML文檔的對(duì)象模型,可用于直接訪問(wèn)XML文檔的各個(gè)部分。它是一次性全部將內(nèi)容加載在內(nèi)存中,生成一個(gè)樹(shù)狀結(jié)構(gòu),它沒(méi)有涉及回調(diào)和復(fù)雜的狀態(tài)管理。 缺點(diǎn)是加載大文檔時(shí)效率低下。

Pull內(nèi)置于Android系統(tǒng)中。也是官方解析布局文件所使用的方式。Pull與SAX有點(diǎn)類(lèi)似,都提供了類(lèi)似的事件,如開(kāi)始元素和結(jié)束元素。不同的是,SAX的事件驅(qū)動(dòng)是回調(diào)相應(yīng)方法,需要提供回調(diào)的方法,而后在SAX內(nèi)部自動(dòng)調(diào)用相應(yīng)的方法。而Pull解析器并沒(méi)有強(qiáng)制要求提供觸發(fā)的方法。因?yàn)樗|發(fā)的事件不是一個(gè)方法,而是一個(gè)數(shù)字。它使用方便,效率高。

SAX、DOM、Pull的比較: 

1. 內(nèi)存占用:SAX、Pull比DOM要好; 
2. 編程方式:SAX采用事件驅(qū)動(dòng),在相應(yīng)事件觸發(fā)的時(shí)候,會(huì)調(diào)用用戶(hù)編好的方法,也即每解析一類(lèi)XML,就要編寫(xiě)一個(gè)新的適合該類(lèi)XML的處理類(lèi)。DOM是W3C的規(guī)范,Pull簡(jiǎn)潔。 
3. 訪問(wèn)與修改:SAX采用流式解析,DOM隨機(jī)訪問(wèn)。 
4. 訪問(wèn)方式:SAX,Pull解析的方式是同步的,DOM逐字逐句

這里不做詳細(xì)講解,看注釋?zhuān)洗a

看項(xiàng)目文件,注意XML放的位置,不會(huì)建assets參考http://www.dbjr.com.cn/article/144766.htm


XML

<?xml version="1.0" encoding="UTF-8" ?>
<persons>
  <person id="23">
    <name>李雷</name>
    <age>30</age>
  </person>
  <person id="20">
    <name>韓梅梅</name>
    <age>25</age>
  </person>
</persons>

person.Java

public class Person {
  Integer id;
  String name;
  Short age;

  public Integer getId() {
    return id;
  }

  public void setId(Integer id) {
    this.id = id;
  }

  public String getName() {
    return name;
  }

  public void setName(String name) {
    this.name = name;
  }

  public Short getAge() {
    return age;
  }

  public void setAge(Short age) {
    this.age = age;
  }

  @Override
  public String toString() {
    return "Person{" +
        "id=" + id +
        ", name='" + name + '\'' +
        ", age=" + age +
        '}';
  }
}

XMLtoEntityActivity

public class XMLtoEntityActivity extends AppCompatActivity {
  private TextView tv_show_entity;
  private String string = "";
  @Override
  protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.xmlto_entity_activity);
    tv_show_entity = (TextView) findViewById(R.id.tv_show_entity);
  }

  public void startXML(View view){
//    SAXService saxService = new SAXService();
//    DOMService domService = new DOMService();
    PULLService pullService = new PULLService();
    try {
      InputStream inputStream = getAssets().open("Users.xml");
//      List<Person> persons = saxService.getPerson(inputStream);
//      List<Person> persons = domService.getPersons(inputStream);
      List<Person> persons = pullService.getPersons(inputStream);
      for (Person person : persons) {
        Log.e("TAG",person.toString());
        string += person.toString();
      }
    } catch (IOException e) {
      e.printStackTrace();
    } catch (Exception e) {
      e.printStackTrace();
    }
    tv_show_entity.setText(string);
  }
}

DOM方法

/**
 * 采用DOM解析XML內(nèi)容
 */

public class DOMService {
  public List<Person> getPersons(InputStream inputStream) throws Exception {

    List<Person> persons = new ArrayList<>();

    //獲取DOM解析器工廠
    DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance();
    //獲DOM解析器
    DocumentBuilder builder = factory.newDocumentBuilder();
    //將解析樹(shù)放入內(nèi)存,通過(guò)返回值Document來(lái)描述結(jié)果
    Document document = builder.parse(inputStream);
    //取得根元素<personos>
    Element root = document.getDocumentElement();
    //取得所有person節(jié)點(diǎn)集合
    NodeList personNodes = root.getElementsByTagName("person");
    for (int i = 0; i < personNodes.getLength(); i++) {
      Person person = new Person();
      //取得person節(jié)點(diǎn)元素
      Element personElement = (Element) personNodes.item(i);
      //取得屬性值并設(shè)置ID
      person.setId(Integer.parseInt(personElement.getAttribute("id")));
      //獲取person的子節(jié)點(diǎn)
      NodeList personChilds = personElement.getChildNodes();
      for (int j = 0; j < personChilds.getLength(); j++) {
        //判斷當(dāng)前節(jié)點(diǎn)是否是元素類(lèi)型的節(jié)點(diǎn)
        if (personChilds.item(j).getNodeType() == Node.ELEMENT_NODE) {
          Element childElement = (Element) personChilds.item(j);
          if ("name".equals(childElement.getNodeName())) {
            //獲取孫節(jié)點(diǎn)的值
            person.setName(childElement.getFirstChild().getNodeValue());
          } else if ("age".equals(childElement.getNodeName())) {
            person.setAge(Short.parseShort(childElement.getFirstChild().getNodeValue()));
          }
        }
      }
      persons.add(person);
    }
    return persons;
  }
}

PULL方法

/**
 * 采用PULL解析XML內(nèi)容
 */

public class PULLService {
  public List<Person> getPersons(InputStream inputStream) throws Exception {
    List<Person> persons = null;
    Person person = null;
    //得到PULL解析器
    XmlPullParser parser = Xml.newPullParser();
    parser.setInput(inputStream,"UTF-8");
    //產(chǎn)生事件
    int eventType = parser.getEventType();
    //如果不是文檔結(jié)束事件就循環(huán)推進(jìn)
    while (eventType != XmlPullParser.END_DOCUMENT) {
      switch (eventType) {
        case XmlPullParser.START_DOCUMENT://開(kāi)始文檔事件
          persons = new ArrayList<>();
          break;
        case XmlPullParser.START_TAG://開(kāi)始元素事件
          //獲取解析器當(dāng)前指向的元素的名稱(chēng)
          String name = parser.getName();
          if ("person".equals(name)) {
            person = new Person();
            person.setId(Integer.parseInt(parser.getAttributeValue(0)));
          }
          if (person != null) {
            if ("name".equals(name)) {
              //獲取解析器當(dāng)前指向元素的下一個(gè)文本節(jié)點(diǎn)的值
              person.setName(parser.nextText());
            }
            if ("age".equals(name)) {
              person.setAge(Short.parseShort(parser.nextText()));
            }
          }
          break;
        case XmlPullParser.END_TAG://結(jié)束元素事件
          //判斷是都是person的結(jié)束事件
          if ("person".equals(parser.getName())) {
            persons.add(person);
            person = null;
          }
          break;
      }
      //進(jìn)入下一個(gè)元素并觸發(fā)相應(yīng)的事件
      eventType = parser.next();
    }
    return persons;
  }
}

SAX方法

/**
 * 采用SAX解析XML內(nèi)容
 */

public class SAXService {
  public List<Person> getPerson(InputStream inputStream) throws Exception {
    //得到SAX解析工廠
    SAXParserFactory factory = SAXParserFactory.newInstance();
    //得到SAX解析器
    SAXParser parser = factory.newSAXParser();
    PersonParser personParser = new PersonParser();
    parser.parse(inputStream,personParser);
    inputStream.close();
    return personParser.getPersons();
  }
  private final class PersonParser extends DefaultHandler {

    private List<Person> persons = null;
    private String tag = null;//記錄當(dāng)前解析到了那個(gè)元素節(jié)點(diǎn)名稱(chēng)
    private Person person;

    public List<Person> getPersons(){
      return persons;
    }
    //一開(kāi)始會(huì)執(zhí)行這個(gè)方法,所以在這里面完成初始化
    @Override
    public void startDocument() throws SAXException {
      persons = new ArrayList<>();
    }

    @Override
    public void startElement(String uri, String localName, String qName, Attributes attributes) throws SAXException {
      //判斷元素節(jié)點(diǎn)是否等于person
      if ("person".equals(localName)) {
        person = new Person();
        //獲取數(shù)據(jù),參數(shù)為索引下標(biāo)
        person.setId(Integer.parseInt(attributes.getValue(0)));
      }
      tag = localName;
    }

    @Override
    public void endElement(String uri, String localName, String qName) throws SAXException {
      if ("person".equals(localName)) {
        persons.add(person);
        person = null;
      }
      tag = null;
    }

    @Override
    public void characters(char[] ch, int start, int length) throws SAXException {
      if (tag != null) {
        //獲取文本節(jié)點(diǎn)的數(shù)據(jù)
        String data = new String(ch, start, length);
        if ("name".equals(tag)) {
          person.setName(data);
        } else if ("age".equals(tag)) {
          person.setAge(Short.parseShort(data));
        }
      }
    }
  }
}

總結(jié):Android開(kāi)發(fā)主流是傳json,而XML解析一般跟網(wǎng)絡(luò)請(qǐng)求,爬蟲(chóng)數(shù)據(jù)相關(guān)。當(dāng)然兩者也是可以相互轉(zhuǎn)換的,Java只強(qiáng)大在于提供了很多的類(lèi)和方法。只要你愿意學(xué),方法總是有的

源碼下載歡迎Star(updating):https://github.com/JinBoy23520/CoderToDeveloperByTCLer

以上就是本文的全部?jī)?nèi)容,希望對(duì)大家的學(xué)習(xí)有所幫助,也希望大家多多支持腳本之家。

相關(guān)文章

最新評(píng)論