AsyncTask案例——异步加载ListView内容,包括优化

1. 第一步:创建ListView中每一项item的页面布局itemlayout.xml:

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:orientation="horizontal"
    android:padding="4dp" >

    <ImageView
        android:id="@+id/iv_icon"
        android:layout_width="64dp"
        android:layout_height="64dp"
        android:src="@drawable/ic_launcher" />

    <LinearLayout
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:gravity="center"
        android:orientation="vertical"
        android:paddingLeft="4dp" >

        <TextView
            android:id="@+id/tv_title"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:maxLines="1"
            android:text="Title"
            android:textSize="15sp" />

        <TextView
            android:id="@+id/tv_content"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:maxLines="3"
            android:text="Content"
            android:textSize="10sp" />
    </LinearLayout>

</LinearLayout>


第二步:设置主页面布局activity_main.xml:包含一个ListView控件:

<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:paddingBottom="@dimen/activity_vertical_margin"
    android:paddingLeft="@dimen/activity_horizontal_margin"
    android:paddingRight="@dimen/activity_horizontal_margin"
    android:paddingTop="@dimen/activity_vertical_margin"
    tools:context=".MainActivity" >

    <ListView
        android:id="@+id/lv_main"
        android:layout_width="match_parent"
        android:layout_height="match_parent" />

</RelativeLayout>


第三步:了解JSON是什么东东:

输入网站打开:http://www.imooc.com/api/teacher?type=4&num=30

然后理应看到这样的JSON页面:

如果显示出来这样的:

那可以复制代码到一些网站中去在线解析,例如:http://json.cn/

那么在这个例子中,我们将其中的name作为Title,description作为Content,picSmall作为ImageView。嗯嗯。


第四步:创建NewsBean.java文件用于封装JSON中的数据,便于使用:

package com.example.asynctaskdemo2;

/*
 * 用于封装JSON中的数据,便于使用:
 * */
public class NewsBean {

	public String newsIconUrl;
	public String newsTitle;
	public String newsContent;
	
}


第五步:将JSON中的数据加载到程序中来:别忘了添加INTERNET访问网络权限:

package com.example.asynctaskdemo2;

import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.io.UnsupportedEncodingException;
import java.util.ArrayList;
import java.util.List;
import java.net.MalformedURLException;
import java.net.URL;

import android.os.AsyncTask;
import android.os.Bundle;
import android.app.Activity;
import android.util.Log;
import android.view.Menu;
import android.widget.ListView;

public class MainActivity extends Activity {

	private ListView mListView;
	private static String URL = "http://www.imooc.com/api/teacher?type=4&num=30";
	
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        
        mListView = (ListView) findViewById(R.id.lv_main);
        new NewAsyncTask().execute(URL);
    }
    
    private List<NewsBean> getJsonData(String url){
    	List<NewsBean> newsBeanList = new ArrayList<NewsBean>();
    	// readStream此句功能与url.openConnection().getInputStream()相同
    	// 可根据URL直接联网获取网络数据,简单粗暴!
    	// 返回值类型为InputStream。
    	// 用URL必须前面引入:import java.net.URL;
    	String jsonString = null;
		try {
			jsonString = readStream(new URL(url).openStream());
		} catch (MalformedURLException e) {
			e.printStackTrace();
		} catch (IOException e) {
			e.printStackTrace();
		}
		
    	Log.d("xys",jsonString);// 打印获取信息
	return newsBeanList;
    }
    
    /*
     * 通过InputStream去读取网络信息:
     * 传来的参数是一个InputStream的字节流is,
     * 通过InputStreamReader将字节流转化为字符流,
     * 再通过BufferedReader将字符流以Buffer的形式读取出来,
     * 最终拼接到result里面。
     * 这样就完成了整个数据的读取。
     * */
    private String readStream(InputStream is){
    	InputStreamReader isr;
    	String result = "";
    	try {
    		String line = "";
			isr = new InputStreamReader(is,"utf-8");
			BufferedReader br = new BufferedReader(isr);
			while((line=br.readLine()) != null){
				result += line;
			}
		} catch (UnsupportedEncodingException e) {
			e.printStackTrace();
		} catch (IOException e) {
			e.printStackTrace();
		}
    	
    	return result;
    }
    
    /*
     * 定义内部类:
     * <Params, Progress, Result>
     * */
    class NewAsyncTask extends AsyncTask<String, Void, List<NewsBean>>{

		@Override
		protected List<NewsBean> doInBackground(String... params) {
			// params[0]为请求网站,因为只传了一个网址,所以只取0即可。
			return getJsonData(params[0]);
		}
    	
    }
}
效果图:


第六步:解析JSON数据到List中:主要改动在getJsonData中,最终将结果存储在NewsBeanList中并返回:

package com.example.asynctaskdemo2;

import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.io.UnsupportedEncodingException;
import java.util.ArrayList;
import java.util.List;
import java.net.MalformedURLException;
import java.net.URL;

import org.json.JSONArray;
import org.json.JSONException;
import org.json.JSONObject;

import android.os.AsyncTask;
import android.os.Bundle;
import android.app.Activity;
import android.util.Log;
import android.view.Menu;
import android.widget.ListView;

public class MainActivity extends Activity {

	private ListView mListView;
	private static String URL = "http://www.imooc.com/api/teacher?type=4&num=30";

	@Override
	protected void onCreate(Bundle savedInstanceState) {
		super.onCreate(savedInstanceState);
		setContentView(R.layout.activity_main);

		mListView = (ListView) findViewById(R.id.lv_main);
		new NewAsyncTask().execute(URL);
	}

	/*
     * 将url对应的JSON格式数据转化为我们所封装的NewsBean对象
	 */
	private List<NewsBean> getJsonData(String url) {
		List<NewsBean> newsBeanList = new ArrayList<NewsBean>();
		// 此句功能与url.openConnection().getInputStream()相同
		// 可根据URL直接联网获取网络数据,简单粗暴!
		// 返回值类型为InputStream。
		// 用URL必须前面引入:import java.net.URL;
		String jsonString = null;
		try {
			jsonString = readStream(new URL(url).openStream());
			JSONObject jsonObject;
			NewsBean newsBean;
			try {
				// 这边很神奇啊,
				jsonObject = new JSONObject(jsonString);
				JSONArray jsonArray = jsonObject.getJSONArray("data");
				for (int i = 0; i < jsonArray.length(); i++) {
					jsonObject = jsonArray.getJSONObject(i);
					newsBean = new NewsBean();
					newsBean.newsIconUrl = jsonObject.getString("picSmall");
					newsBean.newsTitle = jsonObject.getString("name");
					newsBean.newsContent = jsonObject.getString("description");
					newsBeanList.add(newsBean);
				}
			} catch (JSONException e) {
				e.printStackTrace();
			}

		} catch (MalformedURLException e) {
			e.printStackTrace();
		} catch (IOException e) {
			e.printStackTrace();
		}

		// Log.d("xys",jsonString);
		return newsBeanList;
	}

	/*
	 * 通过InputStream去解析读取网络信息: 传来的参数是一个InputStream的字节流is,
	 * 通过InputStreamReader将字节流转化为字符流, 再通过BufferedReader将字符流以Buffer的形式读取出来,
	 * 最终拼接到result里面。 这样就完成了整个数据的读取。
	 */
	private String readStream(InputStream is) {
		InputStreamReader isr;
		String result = "";
		try {
			String line = "";
		
  • 0
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值