转载自http://blog.csdn.net/yangzl2008/article/details/7863938
做Android开发,ListView是最常见不过了,因此对于ListView的自定义Adapter写法,应该也非常的熟悉,高效的Adapter编码,会使得携带大量ListView的数据展现显得非常容易。关于Adapter的写法,网上也有很多的例子,在此不再唠叨。为了提高ListView重绘时对已有对象的复用大抵是这样的:
- @Override
- public View getView(final int position, View convertView, ViewGroup parent) {
- ViewHolder holder = null;
- if (convertView == null) {
- convertView = View.inflate(mContext, R.layout.listview_item, null);
- holder = new ViewHolder();
- holder.no = (TextView) convertView.findViewById(R.id.no);
- holder.click = (TextView) convertView.findViewById(R.id.click);
- convertView.setTag(holder);
- } else {
- holder = (ViewHolder) convertView.getTag();
- }
- String value = list.get(position);
- holder.no.setText(value);
- OnClick listener = new OnClick(position);
- holder.click.setOnClickListener(listener);
- Log.d(TAG,
- "position is " + position + " listener is "
- + listener.toString());
- return convertView;
- }
普遍写法:
- package com.yang.listviewclick.adapter;
- import java.util.List;
- import android.content.Context;
- import android.util.Log;
- import android.view.View;
- import android.view.ViewGroup;
- import android.view.View.OnClickListener;
- import android.widget.BaseAdapter;
- import android.widget.TextView;
- import com.yang.listviewclick.R;
- public class IneffectiveListViewAdapter extends BaseAdapter {
- private Context mContext;
- private List<String> list = null;
- private static final String TAG = "ListViewAdapter";
- public IneffectiveListViewAdapter(Context mContext, List<String> list) {
- this.mContext = mContext;
- this.list = list;
- }
- @Override
- public int getCount() {
- return list.size();
- }
- @Override
- public Object getItem(int position) {
- return list.get(position);
- }
- @Override
- public long getItemId(int position) {
- return 0;
- }
- class ViewHolder {
- TextView no;
- TextView click;
- }
- @Override
- public View getView(final int position, View convertView, ViewGroup parent) {
- ViewHolder holder = null;
- if (convertView == null) {
- convertView = View.inflate(mContext, R.layout.listview_item, null);
- holder = new ViewHolder();
- holder.no = (TextView) convertView.findViewById(R.id.no);
- holder.click = (TextView) convertView.findViewById(R.id.click);
- convertView.setTag(holder);
- } else {
- holder = (ViewHolder) convertView.getTag();
- }
- String value = list.get(position);
- holder.no.setText(value);
- //问题出在这里,对于每次重绘,都新建了一个listener对象进行处理
- OnClick listener = new OnClick(position);
- holder.click.setOnClickListener(listener);
- Log.d(TAG,
- "position is " + position + " listener is "
- + listener.toString());
- return convertView;
- }
- class OnClick implements OnClickListener {
- private int position;
- public OnClick(int position){
- this.position = position;
- }
- @Override
- public void onClick(View v) {
- Log.d(TAG, list.get(position));
- }
- }
- }
大家知道
- position is 19 listener is com.yang.listviewclick.adapter.IneffectiveListViewAdapter$OnClick@4057f250
推荐写法:
- package com.yang.listviewclick.adapter;
- import java.util.List;
- import com.yang.listviewclick.R;
- import android.content.Context;
- import android.util.Log;
- import android.view.View;
- import android.view.View.OnClickListener;
- import android.view.ViewGroup;
- import android.widget.BaseAdapter;
- import android.widget.TextView;
- public class EffectiveListViewAdapter extends BaseAdapter {
- private Context mContext;
- private List<String> list = null;
- private static final String TAG = "ListViewAdapter";
- public EffectiveListViewAdapter(Context mContext, List<String> list) {
- this.mContext = mContext;
- this.list = list;
- }
- @Override
- public int getCount() {
- return list.size();
- }
- @Override
- public Object getItem(int position) {
- return list.get(position);
- }
- @Override
- public long getItemId(int position) {
- return 0;
- }
- class ViewHolder {
- TextView no;
- TextView click;
- }
- @Override
- public View getView(final int position, View convertView, ViewGroup parent) {
- ViewHolder holder = null;
- OnClick listener = null;
- if (convertView == null) {
- convertView = View.inflate(mContext, R.layout.listview_item, null);
- holder = new ViewHolder();
- holder.no = (TextView) convertView.findViewById(R.id.no);
- holder.click = (TextView) convertView.findViewById(R.id.click);
- listener = new OnClick();//在这里新建监听对象
- holder.click.setOnClickListener(listener);
- convertView.setTag(holder);
- convertView.setTag(holder.click.getId(), listener);//对监听对象保存
- } else {
- holder = (ViewHolder) convertView.getTag();
- listener = (OnClick) convertView.getTag(holder.click.getId());//重新获得监听对象
- }
- String value = list.get(position);//设置监听对象的值
- holder.no.setText(value);
- listener.setPosition(position);
- Log.d(TAG,
- "position is " + position + " listener is "
- + listener.toString());
- return convertView;
- }
- class OnClick implements OnClickListener {
- int position;
- public void setPosition(int position) {
- this.position = position;
- }
- @Override
- public void onClick(View v) {
- Log.d(TAG, list.get(position));
- }
- }
- }
大家可以看到,这里监听对象实现了复用。每次滑动都是第一次创建的监听对象的复用。
实现这种机制的关键就是,使用convertView.setTag(holder.click.getId(), listener);对已有的对象进行保存,同时在使用时,使用listener = (OnClick) convertView.getTag(holder.click.getId())再获得这些对象。同时对这些复用的对象赋予不同的值listener.setPosition(position);。好了,今天就说到这里,测试项目的下载地址如下。
项目下载地址
版权声明:本文为博主原创文章,未经博主允许不得转载。