日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

ListView的使用用ViewHolder提升效率

發布時間:2023/12/2 编程问答 32 豆豆
生活随笔 收集整理的這篇文章主要介紹了 ListView的使用用ViewHolder提升效率 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

public class

ListView

extends AbsListView
java.lang.Object
????android.view.View
?????android.view.ViewGroup
??????android.widget.AdapterView<T?extends?android.widget.Adapter>
???????android.widget.AbsListView
????????android.widget.ListView

Class Overview

A view that shows items in a vertically scrolling list. The items come from theListAdapter associated with this view.

?

public class

ArrayAdapter

extends BaseAdapter
implements Filterable

java.lang.Object
????android.widget.BaseAdapter
?????android.widget.ArrayAdapter<T>
Class Overview

A concrete BaseAdapter that is backed by an array of arbitrary objects. By default this class expects that the provided resource id references a single TextView. If you want to use a more complex layout, use the constructors that also takes a field id. That field id should reference a TextView in the larger layout resource.

However the TextView is referenced, it will be filled with the toString() of each object in the array. You can add lists or arrays of custom objects. Override the toString() method of your objects to determine what text will be displayed for the item in the list.

To use something other than TextViews for the array display, for instance, ImageViews, or to have some of data besides toString() results fill the views, overridegetView(int, View, ViewGroup) to return the type of view you want.

?

1、ListView的簡單使用

Demo:

activity_main.xml

<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="sunny.example.listviewsimple.MainActivity" ><ListViewandroid:id="@+id/list_view"android:layout_width="match_parent"android:layout_height="match_parent"/></RelativeLayout>

?

MainActivity.java

package sunny.example.listviewsimple;import android.support.v7.app.ActionBarActivity; import android.os.Bundle; import android.widget.ArrayAdapter; import android.widget.ListView;public class MainActivity extends ActionBarActivity {private String[] data = {"Apple","Banana","Orange","Watermelon","Pear","Grape","Pineapple","Strawberry","Cherry","Mango"};@Overrideprotected void onCreate(Bundle savedInstanceState) {super.onCreate(savedInstanceState);setContentView(R.layout.activity_main);ArrayAdapter<String> adapter = new ArrayAdapter<String>(MainActivity.this, android.R.layout.simple_list_item_1, data);ListView listView = (ListView)findViewById(R.id.list_view);listView.setAdapter(adapter);} }


2、提升ListView的運行效率ViewHolder、自定義ListView的界面(例:包括一個ImageView和一個TextView)

?

上例一個item只能顯示一段文本,現在自定義一個ListView的界面。自定義一個Fruit類,作為ListView適配器的適配類型。

Fruit.java

package com.example.listviewtest;public class Fruit {private String name;private int imageId;public Fruit(String name,int imageId){this.name = name;this.imageId = imageId;}public String getName(){return name;}public int getImageId(){return imageId;}}

Fruit類有兩個字段,name表示水果的名字,iamgeId表示水果對應的圖片資源id。

然后為ListView的item自定義一個布局

fruit_item.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="match_parent"><ImageViewandroid:id="@+id/fruit_image"android:layout_width="wrap_content"android:layout_height="wrap_content"/><TextViewandroid:id="@+id/fruit_name"android:layout_width="wrap_content"android:layout_height="wrap_content"android:layout_gravity="center"android:layout_marginLeft="10dip"/> </LinearLayout> 子item布局中定義一個ImageView用于顯示水果圖片,TextView用于顯示水果名字。 創建一個自定義適配器FruitAdapter繼承自ArrayAdapter,將泛型指定為Fruit類。 ? FruitAdapter中用到的類與方法: public abstract class

LayoutInflater

extends Object
java.lang.Object
????android.view.LayoutInflater

Class Overview

Instantiates a layout XML file into its corresponding View objects. It is never used directly. Instead, usegetLayoutInflater() orgetSystemService(String) to retrieve a standard LayoutInflater instance that is already hooked up to the current context and correctly configured for the device you are running on. For example:

LayoutInflater inflater = (LayoutInflater)context.getSystemService(Context.LAYOUT_INFLATER_SERVICE);

public static LayoutInflater from (Context context)

Added in API level 1

Obtains the LayoutInflater from the given context.

public View inflate (int resource,ViewGroup root)

Added in API level 1

Inflate a new view hierarchy from the specified xml resource. Throws InflateException if there is an error.

Parameters
resourceroot
ID for an XML layout resource to load (e.g., R.layout.main_page)
Optional view to be the parent of the generated hierarchy.
Returns
  • The root View of the inflated hierarchy. If root was supplied, this is the root View; otherwise it is the root of the inflated XML file.
? FruitAdapter.java public class FruitAdapter extends ArrayAdapter<Fruit> {private int resourceId;public FruitAdapter(Context context,int textViewResourceId,List<Fruit> objects){super(context,textViewResourceId,objects);resourceId = textViewResourceId;}@Overridepublic View getView(int position,View convertView,ViewGroup parent){//得到當前項的Fruit實例Fruit fruit = getItem(position);//LayoutInflater來為這個子項加載布局View view = LayoutInflater.from(getContext()).inflate(resourceId,null);ImageView fruitImage = (ImageView) view.findViewById(R.id.fruit_image);TextView textView = (TextView) view.findViewById(R.id.fruit_name);fruitImage.setImageResource(fruit.getImageId());fruitName.setText(fruit.getName());return view;} }
重寫了ArrayAdapter的 getView()方法,這個方法在每個子item被滾動到屏幕內的時候會被調用。

目前ListView的運行效率是很低的,因為每個子item被滾動到屏幕內的時候會調用getView()在getView()方法中每次都將布局加載了一遍。

優化方法一:

public View getView(int position,View convertView,ViewGroup parent)

方法中有一個convertView參數,用于將之前加載好的布局進行緩存,以便以后重用。

修改上述代碼:

?

public class FruitAdapter extends ArrayAdapter<Fruit> {private int resourceId;public FruitAdapter(Context context,int textViewResourceId,List<Fruit> objects){super(context,textViewResourceId,objects);resourceId = textViewResourceId;}@Overridepublic View getView(int position,View convertView,ViewGroup parent){//得到當前項的Fruit實例Fruit fruit = getItem(position);View view;//convertView為空,使用LayoutInflater加載布局//不為空,則直接對convertView進行重用if(convertView==null){view = LayoutInflater.from(getContext()).inflate(resourceId, null);}else{view = convertView;}ImageView fruitImage = (ImageView) view.findViewById(R.id.fruit_image);TextView textView = (TextView) view.findViewById(R.id.fruit_name);fruitImage.setImageResource(fruit.getImageId());fruitName.setText(fruit.getName());return view;} }

?

目前代碼還可以優化,雖然現在已經不會再重復去加載布局,但每次getView()方法中還是會調用View的findViewById()來獲取一次控件實例。下面使用ViewHolder繼續優化:

優化方法二:新增一個內部類ViewHolder: ? class ViewHolder{ImageView fruitImage;TextView fruitName;}
用于對對象的實例進行緩存。當convertView為空,創建一個ViewHolder對象,并將控件的實例都存放在ViewHolder里,然后調用View的setTag()方法將ViewHolder 對象存儲在view中。當convertView不為空時,調用View的getTag()方法把ViewHolder取出。這樣所有的控件實例都緩存在ViewHolder里了,就不用每次都通過findViewById()方法獲取控件實例了。 ? FruitAdapter.java package com.example.listviewtest;import java.util.List;import android.annotation.SuppressLint; import android.content.Context; import android.view.LayoutInflater; import android.view.View; import android.view.ViewGroup; import android.widget.ArrayAdapter; import android.widget.ImageView; import android.widget.TextView;@SuppressLint("ViewHolder") public class FruitAdapter extends ArrayAdapter<Fruit> {private int resourceId;public FruitAdapter(Context context,int textViewResourceId,List<Fruit> objects){super(context,textViewResourceId,objects);resourceId = textViewResourceId;}@Overridepublic View getView(int position,View convertView,ViewGroup parent){Fruit fruit = getItem(position);View view;ViewHolder viewHolder;if(convertView==null){view = LayoutInflater.from(getContext()).inflate(resourceId, null);viewHolder = new ViewHolder();viewHolder.fruitImage = (ImageView)view.findViewById(R.id.fruit_image);viewHolder.fruitName = (TextView) view.findViewById(R.id.fruit_name);view.setTag(viewHolder);}else{view = convertView;viewHolder = (ViewHolder)view.getTag();}//View view = LayoutInflater.from(getContext()).inflate(resourceId,null);//ImageView fruitImage = (ImageView) view.findViewById(R.id.fruit_image);//TextView fruitName = (TextView) view.findViewById(R.id.fruit_name);//fruitImage.setImageResource(fruit.getImageId());//fruitName.setText(fruit.getName());viewHolder.fruitImage.setImageResource(fruit.getImageId());viewHolder.fruitName.setText(fruit.getName());return view;}class ViewHolder{ImageView fruitImage;TextView fruitName;}}
activity_main.xml ? <LinearLayout 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"><ListViewandroid:id="@+id/list_view"android:layout_width="match_parent"android:layout_height="match_parent"></ListView></LinearLayout> ? MainActivity.java package com.example.listviewtest;import java.util.ArrayList; import java.util.List;import android.app.Activity; import android.content.Context; //import android.support.v7.app.ActionBarActivity; import android.os.Bundle; import android.view.View; import android.widget.AdapterView; import android.widget.AdapterView.OnItemClickListener; import android.widget.ArrayAdapter; import android.widget.Toast;import android.widget.ListView;public class MainActivity extends Activity {private String[] data = {"Apple","Banana","Orange","Watermelon","Pear","Grape","Pineapple","Strawberry","cherry","Mango"};private List<Fruit> fruitList = new ArrayList<Fruit>();@Overrideprotected void onCreate(Bundle savedInstanceState) {super.onCreate(savedInstanceState);setContentView(R.layout.activity_main);initFruits(); //public FruitAdapter(Context context,int textViewResourceId,List<Fruit> objects) FruitAdapter adapter = new FruitAdapter(MainActivity.this,R.layout.fruit_item,fruitList);//ArrayAdapter<String> adapter = new ArrayAdapter<String>(MainActivity.this,android.R.layout.simple_list_item_1,data);ListView listView = (ListView) findViewById(R.id.list_view);listView.setAdapter(adapter);listView.setOnItemClickListener(new OnItemClickListener(){@Overridepublic void onItemClick(AdapterView<?> parent, View view,int position, long id) {// TODO Auto-generated method stubFruit fruit = fruitList.get(position);Toast.makeText(MainActivity.this, fruit.getName(), Toast.LENGTH_SHORT).show();}});}private void initFruits() {// TODO Auto-generated method stubFruit apple = new Fruit("Apple",R.drawable.ic_launcher);fruitList.add(apple);Fruit banana = new Fruit("Banana",R.drawable.ic_launcher1);fruitList.add(banana);Fruit orange = new Fruit("Orange",R.drawable.ic_launcher2);fruitList.add(orange);Fruit Watermelon = new Fruit("Watermelon",R.drawable.ic_launcher3);fruitList.add(Watermelon);Fruit Pear = new Fruit("Pear",R.drawable.ic_launcher4);fruitList.add(Pear);Fruit Grape = new Fruit("Grape",R.drawable.ic_launcher5);fruitList.add(Grape);Fruit Pineapple = new Fruit("Pineapple",R.drawable.ic_launcher6);fruitList.add(Pineapple);Fruit Strawberry = new Fruit("S trawberry",R.drawable.ic_launcher7);fruitList.add(Strawberry);Fruit cherry = new Fruit("Cherry",R.drawable.ic_launcher8);fruitList.add(cherry);Fruit mango = new Fruit("Mango",R.drawable.ic_launcher9);fruitList.add(mango);} }


?

?

?


總結

以上是生活随笔為你收集整理的ListView的使用用ViewHolder提升效率的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。