android 面试之listview

来源:互联网 发布:美工学徒招聘 编辑:程序博客网 时间:2024/06/05 19:49
ListView优化一直是一个老生常谈的问题,不管是面试还是平常的开发中,ListView永远不会被忽略掉,那么这篇文章我们来看看如何最大化的优化ListView的性能。· 1.在adapter中的getView方法中尽量少使用逻辑· 2.尽最大可能避免GC· 3.滑动的时候不加载图片· 4.将ListView的scrollingCache和animateCache设置为false· 5.item的布局层级越烧越好· 6.使用ViewHolder1.在adapter中的getView方法中尽量少使用逻辑不要在你的getView()中写过多的逻辑代码,我们可以将这些代码放在别的地方,例如:


[html] view plain copy
print?在CODE上查看代码片派生到我的代码片
  1. public View getView(int position, View convertView, ViewGroup parent) {  
  2. View item = mInflater.inflate(R.layout.list_item_icon_text, null);  
  3. ((TextView) item.findViewById(R.id.text)).setText(DATA[position]);  
  4. ((ImageView) item.findViewById(R.id.icon)).setImageBitmap(  
  5. (position & 1) == 1 ? mIcon1 : mIcon2);  
  6. return item;  
  7. }  
怎么样?如果超过1000000项时,后果不堪设想!您可千万别这么写!
[html] view plain copy
print?在CODE上查看代码片派生到我的代码片
  1. public View getView(int position, View convertView, ViewGroup parent) {  
  2. if (convertView == null) {  
  3. convertView = mInflater.inflate(R.layout.item, null);  
  4. }  
  5. ((TextView) convertView.findViewById(R.id.text)).setText(DATA[position]);  
  6. ((ImageView) convertView.findViewById(R.id.icon)).setImageBitmap(  
  7. (position & 1) == 1 ? mIcon1 : mIcon2);  
  8. return convertView;  
  9. }  
那么上面的代码还可以优化吗,答案是肯定的。
[html] view plain copy
print?在CODE上查看代码片派生到我的代码片
  1. public View getView(int position, View convertView, ViewGroup parent) {  
  2. ViewHolder holder;  
  3. if (convertView == null) {  
  4. convertView = mInflater.inflate(R.layout.list_item_icon_text, null);  
  5. holder = new ViewHolder();  
  6. holder.text = (TextView) convertView.findViewById(R.id.text);  
  7. holder.icon = (ImageView) convertView.findViewById(R.id.icon);  
  8. convertView.setTag(holder);  
  9. } else {  
  10. holder = (ViewHolder) convertView.getTag();  
  11. }  
  12. holder.text.setText(DATA[position]);  
  13. holder.icon.setImageBitmap((position & 1) == 1 ? mIcon1 : mIcon2);  
  14. return convertView;  
  15. }  
  16.     
  17. static class ViewHolder {  
  18. TextView text;  
  19. ImageView icon;  
  20. }  

2.GC 垃圾回收器当你创建了大量的对象的时候,GC就会频繁的执行,所以在getView()方法中不要创建很多的对象,最好的优化是,不要在ViewHolder以外创建任何对象,如果你的你的log里面发现“GC has freed some memory”频繁出现的话,那你的程序肯定有问题了。你可以检查一下:a) item布局的层级是否太深b) getView()方法中是否有大量对象存在c) ListView的布局属性3.加载图片如果你的ListView中需要显示从网络上下载的图片的话,我们不要在ListView滑动的时候加载图片,那样会使ListView变得卡顿,所以我们需要再监听器里面监听ListView的状态,如果滑动的时候,停止加载图片,如果没有滑动,则开始加载图片

[html] view plain copy
print?在CODE上查看代码片派生到我的代码片
  1. listView.setOnScrollListener(new OnScrollListener() {  
[html] view plain copy
print?在CODE上查看代码片派生到我的代码片
  1.  @Override  
  2. public void onScrollStateChanged(AbsListView listView,  
  3. int scrollState) { //停止加载图片  
  4. if (scrollState ==  
  5. AbsListView.OnScrollListener.SCROLL_STATE_FLING) {  
  6. imageLoader.stopProcessingQueue();  
  7. } else { //开始加载图片  
  8. imageLoader.startProcessingQueue();  
  9. }  
  10. } @Override  
  11. public void onScroll(AbsListView view, int firstVisibleItem, int visibleItemCount, int totalItemCount) {   
[html] view plain copy
print?在CODE上查看代码片派生到我的代码片
  1. // TODO Auto-generated method stub  
  2. }  
  3. });  

4.将ListView的scrollingCache和animateCache设置为falsescrollingCache: scrollingCache本质上是drawing cache,你可以让一个View将他自己的drawing保存在cache中(保存为一个bitmap),这样下次再显示View的时候就不用重画了,而是从cache中取出。默认情况下drawing cahce是禁用的,因为它太耗内存了,但是它确实比重画来的更加平滑。而在ListView中,scrollingCache是默认开启的,我们可以手动将它关闭。animateCache: ListView默认开启了animateCache,这会消耗大量的内存,因此会频繁调用GC,我们可以手动将它关闭掉,所以我们代码可以这么写:
[html] view plain copy
print?在CODE上查看代码片派生到我的代码片
  1. <ListView  
  2. android:id="@android:id/list"  
  3. android:layout_width="match_parent"  
  4. android:layout_height="wrap_content"  
  5. android:divider="@color/list_background_color"  
  6. android:dividerHeight="0dp"  
  7. android:listSelector="#00000000"  
  8. android:scrollingCache="false"  
  9. android:animationCache="false"  
  10. android:smoothScrollbar="true" />  

5.减少item的布局的深度我们应该尽量减少item布局深度,因为当滑动ListView的时候,这回直接导致测量与绘制,因此会浪费大量的时间,所以我们应该将一些不必要的布局嵌套关系去掉。减少item布局深度,这个我曾经做过一个实验,当布局嵌套超过5层的时候,Android的Decodview就会出现错误,所以请不要嵌套的太深。

6.使用ViewHolder这个大家应该非常熟悉了,但是不要小看这个ViewHolder,它可以大大提高我们ListView的性能ListView的优化我们已经讲完了。

以上是最基本的,如果你还有更好的方案补充,欢迎后面留言。或者加入我们的官方qq群:278792776
0 0
原创粉丝点击