package com.test.king.xmlparser;
import android.annotation.SuppressLint;
import android.app.Activity;
import android.content.res.Resources;
import android.os.Handler;
import android.os.Message;
import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
import android.util.Log;
import android.view.View;
import android.widget.TextView;
import org.xmlpull.v1.XmlPullParser;
import org.xmlpull.v1.XmlPullParserException;
import java.io.IOException;
import java.lang.ref.WeakReference;
import java.util.ArrayList;
import java.util.List;
public class MainActivity extends AppCompatActivity {
private static TextView tvContent;
private static final int MSG_FINISH=0x0001;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
tvContent=findViewById(R.id.tv_content);
}
//内部类解决可能存在的内存溢出
/*
*、本文描述静态和非静态内部类的区别是非静态内部类持有外部类的引用。
二、内部类实例的持有对象的生命周期大于其外部类对象,那么就有可能致使内存泄露。
好比,要实例化一个超出activity生命周期的内部类对象,
避免使用非静态的内部类。建议使用静态内部类而且在内部类中持有外部类的弱引用。
*
* */
//静态内部类
private static class MyHandler extends Handler {
private final WeakReference mActivity;
//构造方法
public MyHandler(MainActivity activity) {
mActivity = new WeakReference(activity);//对外部类的弱引用
}
@Override
public void handleMessage(Message msg) {
MainActivity activity = mActivity.get();
if (activity != null) {
switch (msg.what)
{
case MSG_FINISH:
List contents=(List)msg.obj;
//在主线程中显示
for(String content:contents)
{
tvContent.append(content+"\n");
}
break;
}
}
}
}
//new Handler对象处理消息,下文有引用
private final MyHandler mHandler = new MyHandler(this);
//警告
/*
private Handler handler=new Handler()
{
@Override
//重写handleMessage方法处理消息
public void handleMessage(Message msg) {
switch (msg.what)
{
case MSG_FINISH:
List contents=(List)msg.obj;
//在主线程中显示
for(String content:contents)
{
tvContent.append(content+"\n");
}
break;
}
}
};*/
public void parser(View view) throws IOException, XmlPullParserException {
//常规方法
/*
List contents=getPullParserContent(getResources(),R.xml.words);
for(String content:contents)
{
tvContent.append(content+"\n");
}*/
//解析XML可能须要耗费很长的时间,因此这里单独作一个子线程
new Thread()
{
@Override
//重写run方法
public void run()
{
try {
List contents=getPullParserContent(getResources(),R.xml.words);
//完成工做,通知主线程
Message msg=mHandler.obtainMessage();//也能够new Message
msg.what=MSG_FINISH;
msg.obj=contents;
mHandler.sendMessage(msg);
} catch (IOException e) {
e.printStackTrace();
} catch (XmlPullParserException e) {
e.printStackTrace();
}
}
}.start();
}
private List getPullParserContent(Resources res,int id) throws IOException, XmlPullParserException {
List contents = null;
String tagName;
//XmlPullParser
XmlPullParser parser = res.getXml(id);
//Pull解析本质是SAX解析
int eventType = parser.getEventType();
while (eventType != XmlPullParser.END_DOCUMENT) {
switch (eventType) {
case XmlPullParser.START_DOCUMENT:
Log.i("Test", "START_DOCUMENT");
contents=new ArrayList();
break;
case XmlPullParser.END_DOCUMENT:
break;
case XmlPullParser.START_TAG:
tagName = parser.getName();
if (tagName.equals("word")) {
String value = parser.getAttributeValue(0);
contents.add(value);
Log.i("Test", "START_TAG:" + tagName + " " + value);
}
break;
case XmlPullParser.END_TAG:
tagName = parser.getName();
Log.i("Test", "END_TAG:" + tagName);
break;
}
eventType = parser.next();
}
return contents;
}
}