ListView优化分页优化

缘由

我们在用ListView展现数据的时候。比如展现联系人,如果联系人太多就会出现卡的现象,比如如果有1000多条数据,从数据库里查询,然后装载到List容器这段时间是比较耗时的。虽然我们可以用asyncTask来单独开启一个子线程加载。一次查看那么多,未免有点多余。是否可以通过先装载30条数据,如果用户需要我们在继续查询并且展示后面的数据,这样一来可以提升。使用速率。

实现方法

1、数据库分页查询

首先写SqlHelper指定每次查询数据库多少数据。代码如下

/*** 分页查询黑名单* * @param limit* 限制数量* @param offset* 开始位置* @return*/ public List<BlackNumInfo> getPartBlackNum(int limit, int offset) { //查询返回的数据容器List<BlackNumInfo> blackNums = null; SQLiteDatabase db = dbHelper.getReadableDatabase();

String[] columns = new String[] { NUM, MODE, ID };String selection = null; String[] selectionArgs = null;String groupBy = null; String having = null;String orderBy = null; // 排序功能String limitsr = offset + "," + limit; // 分页数据

Cursor cursor = db.query(TABLE, columns, selection, selectionArgs, groupBy, having,orderBy, limitsr); //如果没有数据就返回View if (cursor.getCount() > 0){blackNums = new ArrayList<BlackNumInfo>();}

while (cursor.moveToNext()){String num = cursor.getString(0); int mode = cursor.getInt(1); int id = cursor.getInt(2);BlackNumInfo b = new BlackNumInfo(num, mode, id);blackNums.add(b);}

db.close();dbHelper.close(); return blackNums;}

2. AsyncTask类的内部优化

  • 思路:每次开启一个异步任务查询数据。

  • 重置适配器中,数据容器的值,刷想适配器
  • ListView重绘
/*** 异步加载*/ public void fillData() { new AsyncTask<String, Integer, String>(){

// 程序运行前 @Override protected void onPreExecute() {mLoadProgressBar.setVisibility(View.VISIBLE); // 显示加载进度 super.onPreExecute();}

// 程序运行时 @Override protected String doInBackground(String... params) { // 查询 前30项的数据: 用子线程 , if (mBlackNumList == null){mBlackNumList = dao.getPartBlackNum(limit, offset);} else{ // 如果不是第一次查询 if (dao.getPartBlackNum(limit, offset) != null){ //把查询到的数据添加到容器中去mBlackNumList.addAll(dao.getPartBlackNum(limit, offset));}}

return null;}

// 运行后 @Override protected void onPostExecute(String result) { //ProgressBar设置为不可见。mLoadProgressBar.setVisibility(View.INVISIBLE);

if (adapter == null){ //第一次加载,创建适配器适配器 adapter = new BlackNumAdapter(context, mBlackNumList);mBlackNumListView.setAdapter(adapter);} else{ //第二次加载,适配器中容器数量adapter.setBlackNumList(mBlackNumList); //发送通知,适配器内容改变,从新加载adapter.notifyDataSetChanged();}}

}.execute();}

3.Adapter优化分页数据

  • 思路

  • convertView可回收视图的再次利用。
  • holderView类保存每次inflate出来View的子控件并保存在convertViewTag中。
  • 添加一个setDate()方法,重置容器数据
public class BlackNumAdapter extends BaseAdapter{List<BlackNumInfo> mBlackNumList;Context context;BlackNumDao dao;

public BlackNumAdapter(Context context, List<BlackNumInfo> mBlackNumList) { this.context = context;dao = new BlackNumDao(context); this.mBlackNumList = mBlackNumList;}

public void setBlackNumList(List<BlackNumInfo> mBlackNumInfos) { this.mBlackNumList = mBlackNumInfos;}

@Override public int getCount() { return mBlackNumList.size();}

@Override public Object getItem(int position) { return mBlackNumList.get(position);}

@Override public long getItemId(int position) { return position;}

@Override public View getView(final int position, View convertView, ViewGroup parent) { // 适配器的优化 final BlackNumInfo numInfo = mBlackNumList.get(position);holderView hV = null; if (convertView == null){hV = new holderView();convertView = LayoutInflater.from(context).inflate(R.layout.item_blacknum, parent, false);hV.modeTextView = (TextView) convertView.findViewById(R.id.tv_mode);hV.numberTextView = (TextView) convertView.findViewById(R.id.tv_number);hV.deleteImageView = (ImageView) convertView.findViewById(R.id.iv_deleteNumber);convertView.setTag(hV);} else{hV = (holderView) convertView.getTag();}

hV.numberTextView.setText(mBlackNumList.get(position).getNum());

String mode = "全部拦截"; switch (numInfo.getMode()){ case BlackNumDao.ALL:mode = "全部链接"; break; case BlackNumDao.CLL:mode = "电话拦截"; case BlackNumDao.SMS:mode = "短信拦截"; default: break;}

hV.modeTextView.setText(mode);hV.deleteImageView.setOnClickListener(new OnClickListener(){ @Override public void onClick(View v) { // 删除功能dao.delete(numInfo.getNum() + "");mBlackNumList.remove(position);notifyDataSetChanged();}}); return convertView;}

}

/*** 包装类* @author H_lang**/class holderView{ public TextView modeTextView; public TextView numberTextView; public ImageView deleteImageView;}

4.ListView滚动监听。

  • liseView设置滚动监听。

  • 重置分页查询的开始标度
 /*** 滚动状态改变的时候。*/ @Override public void onScrollStateChanged(AbsListView view, int scrollState) { // 根据滚动的状态来加载数据。 if (scrollState == OnScrollListener.SCROLL_STATE_TOUCH_SCROLL){ // 获得最后一次显示的数据 int lastVisiblePosition = mBlackNumListView.getLastVisiblePosition(); int size = mBlackNumList.size();

if (lastVisiblePosition == size - 1){ //设置下次查询的开始位置。offset = limit + offset;fillData();}

}

}

总结

其中还是有许多的缺点。还有许多需要优化的功能。但是对于我现在学习的技术,没有想到更好的方法,希望以后我能继续优化,或者重写listView控件。

时间: 2024-12-24 05:06:14

ListView优化分页优化的相关文章

Android ListView复杂列表优化实践

原文:Android ListView复杂列表优化实践 很多社交App都不免会涉及到复杂的列表元素实现,一个列表上面可能大量的图片,不定长的评论列表,给手机端的程序员带来了不少的挑战.本文就是在实现复杂的列表滑动的情况下,利用已知的优化方法指导下的一次优化实践,旨在提升ListView的滑动流畅度,为用户带来良好的体验. 1:设计稿: 这是列表中可能出现的ItemView,有两种,但是又有许多相同的地方,比如一样有点赞的图片,评论等...其中,评论和点赞的数量是可变的. 2:使用一般布局带来的问

MySQL分页优化中的“INNER JOIN方式优化分页算法”到底在什么情况下会生效?

本文出处:http://www.cnblogs.com/wy123/p/7003157.html 最近无意间看到一个MySQL分页优化的测试案例,并没有非常具体地说明测试场景的情况下,给出了一种经典的方案,因为现实中很多情况都不是固定不变的,能总结出来通用性的做法或者说是规律,是要考虑非常多的场景的,同时,面对能够达到优化的方式要追究其原因,同样的做法,换了个场景,达不到优化效果的,还要追究其原因.个人对此场景在不用情况表示怀疑,然后自己测试了一把,果然发现一些问题,同时也证实了一些预期的想法.

ListView复用和优化详解

我们每一个Android开发人员对ListView的使用肯定是很熟悉的,然而多少人能真正的懂ListView的缓存机制呢,说白了就是ListView为了提高效率,而内部实现的一种优化,牺牲一点内存.而这种优化就需要复用ItemView(也就是item对应的View).那么下面楼主来对ListView和RecyclerView的item复用问题做一个深入的讲解先来一张大家学习的时候都遇到过的图这里写图片描述看不懂也没啥事,可以接着往下看,先有一个直观的认识首先来解答几个问题为什么会存在Item复用

SQL通用优化方案(where优化、索引优化、分页优化、事务优化、临时表优化)

SQL通用优化方案:1. 使用参数化查询:防止SQL注入,预编译SQL命令提高效率2. 去掉不必要的查询和搜索字段:其实在项目的实际应用中,很多查询条件是可有可无的,能从源头上避免的多余功能尽量砍掉,这是最简单粗暴的解决方案.3. 选择最有效率的表名顺序: 数据库的解析器按照从右到左的顺序处理FROM子句中的表名,FROM子句中写在最后的表将被最先处理,在FROM子句中包含多个表的情况下,你必须选择记录条数最少的表放在最后,如果有3个以上的表连接查询,那就需要选择那个被其他表所引用的表放在最后.

mysql优化--分页

一般我们通常会order by limit start ,offset的方式进行分页查询. 1一般而言,分页sql的耗时随着start的增加而急剧的增加 例如:select * from a1 limit 100,10 --->0.02s select * from a1 limit 100000,10--->3.02s 可以看出,随着start的急剧增加,耗时成倍的增加,如何优化呢? 一般想要优化分页,最好的解决办法就是:没有分页.或者可以把分页的算法给Sphinx,Lucence等第三方解

分页优化+表锁和库存优化+数据库的备份和导入

一.分页优化技术 代码参看: php/classic.php 把50331651记录进行分页,每页显示2条记录,于是我们用传统php编码方式,编写分页代码如下: 上传到/var/www/html下进行测试,结果如下: 如果访问第1页和第4页,返回语句: 使用explain执行计划查询比较靠前的页数,发觉速度很快因为可以使用上索引: 如果访问第4100000页,返回语句: 使用explain分析结果如下: 发觉这时如果分页到了中间的页数,这时我们既需要排序又要分页检索数据的时候,就会出现Using

由浅入深讲解android开发中listview的性能优化

ListView是一种可以显示一系列项目并能进行滚动显示的View.在每行里,既可以是简单的文本,也可以是复杂的结构.一般情况下,你都需要保证ListView运行得很好(即:渲染更快,滚动流畅).在接下来的内容里,我将就ListView的使用,向大家提供几种解决不同性能问题的解决方案. 如果你想使用ListView,你就不得不使用ListAdapter来显示内容.SDK中,已经有了几种简单实现的Adapter: ·         ArrayAdapter<T> (显示数组对象,使用toStr

php+mysql分页优化版

效果图: 1 <table align="center" cellspacing="2"> 2 <?php 3 include('conn/conn2.php'); 4 $pagesize=10; 5 $url=$_SERVER["REQUEST_URI"];//取当前url路径 6 $url=parse_url($url); //查询当前路径所以值 7 $url=$url[path];//查询当前路径path的值 8 9 $n

mysql limit分页优化方法分享

MySQL的优化是非常重要的.其他最常用也最需要优化的就是limit.MySQL的limit给分页带来了极大的方便,但数据量一大的时候,limit的性能就急剧下降. 同样是取10条数据 select * from yanxue8_visit limit 10000,10 和 select * from yanxue8_visit limit 0,10 就不是一个数量级别的. 网上也很多关于limit的五条优化准则,都是翻译自MySQL手册,虽然正确但不实用.今天发现一篇文章写了些关于limit优