Android: The triple realm of ListView caching mechanism and BaseAdapter (comma, common, literary)

Keywords: Android xml Java Mobile

As we all know, the format of listview is certain, and the data sources are indeed diverse. At this time, an adapter is needed to convert the data sources into the format to be displayed by listview.

baseAdapter was born.

The display and caching mechanisms of listview and gridView are as follows

Everyone knows that the size of the screen is limited, but the data in the listview may be a lot, so the mobile phone can not display all the data at once, it only loads the data displayed on the screen.

As shown above, when we slide the screen down, item1 is reclaimed to recycler and item8 is displayed on the screen. item8 takes such a layout file from recycler and resets the data to be displayed by item8 and sets the location to be displayed. In short, a sentence needs to be displayed before it is reclaimed to the cache.

As for the title, what is the difference between the three realms of BaseAdapter (comic, ordinary, literary and artistic)? Just how to use the display and caching mechanism of listview

There is such a method on the adapter of listview

  1. @Override  
  2. public View getView(int position, View convertView, ViewGroup parent) {  
  3.     // TODO Auto-generated method stub  
  4.     return null;  
  5. }  


Among them, the difference between the comma style and the ordinary style of literature and art lies in how to use this method.

Let's take an example to compare the three realms of adapter.

The results to be achieved are as follows


activity_main.xml

  1. <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"  
  2.     android:layout_width="fill_parent"  
  3.     android:layout_height="fill_parent"  
  4.     android:orientation="vertical" >  
  5.     <ListView   
  6.         android:id="@+id/lv_listView"  
  7.         android:layout_width="match_parent"  
  8.         android:layout_height="match_parent"  
  9.         ></ListView>  
  10.   
  11. </LinearLayout>  


item.xml

  1. <?xml version="1.0" encoding="utf-8"?>  
  2. <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"  
  3.     android:layout_width="match_parent"  
  4.     android:layout_height="match_parent" >  
  5.   
  6.     <ImageView  
  7.         android:id="@+id/iv_image"  
  8.         android:layout_width="50dp"  
  9.         android:layout_height="50dp"  
  10.         android:layout_alignParentLeft="true"  
  11.         android:src="@drawable/ic_launcher" />  
  12.   
  13.     <TextView  
  14.         android:id="@+id/tv_nickName"  
  15.         android:layout_width="fill_parent"  
  16.         android:layout_height="wrap_content"  
  17.         android:layout_toRightOf="@id/iv_image"  
  18.         android:gravity="center_horizontal"  
  19.         android:textSize="20sp"  
  20.         android:text="Nickname?" />  
  21.   
  22.     <TextView  
  23.         android:id="@+id/tv_content"  
  24.         android:layout_width="fill_parent"  
  25.         android:layout_height="wrap_content"  
  26.         android:layout_toRightOf="@id/iv_image"  
  27.         android:layout_below="@id/tv_nickName"  
  28.         android:textSize="15sp"  
  29.         android:text="content" />  
  30.   
  31. </RelativeLayout>  


For convenience, I created a myObject object to encapsulate the data to be displayed in item.xml

MyObject.class

  1. package com.example.baseadapter;  
  2.   
  3. import android.widget.ImageView;  
  4. import android.widget.TextView;  
  5.   
  6. public class MyObject {  
  7.     private int imageViewId;  
  8.     private String nickName;  
  9.     private String content;  
  10.   
  11.     public MyObject(int imageViewId, String nickName, String content) {  
  12.         this.imageViewId = imageViewId;  
  13.         this.nickName = nickName;  
  14.         this.content = content;  
  15.     }  
  16.   
  17.     public String getNickName() {  
  18.         return nickName;  
  19.     }  
  20.   
  21.     public String getContent() {  
  22.         return content;  
  23.     }  
  24.   
  25.     public int getImageViewId() {  
  26.         return imageViewId;  
  27.     }  
  28.   
  29. }  


MainActivity.class

  1. package com.example.baseadapter;  
  2.   
  3. import java.util.ArrayList;  
  4. import java.util.List;  
  5.   
  6. import android.os.Bundle;  
  7. import android.app.Activity;  
  8. import android.view.Menu;  
  9. import android.widget.ListView;  
  10.   
  11. public class MainActivity extends Activity {  
  12.     private List<MyObject> list=new ArrayList<MyObject>();  
  13.     private ListView listView;  
  14.     private MyAdapter myAdapter;  
  15.     @Override  
  16.     protected void onCreate(Bundle savedInstanceState) {  
  17.         super.onCreate(savedInstanceState);  
  18.         setContentView(R.layout.activity_main);  
  19.         listView=(ListView) findViewById(R.id.lv_listView);  
  20.         for(int i=0;i<50;i++){  
  21.             list.add(new MyObject(R.drawable.ic_launcher, "Nickname?"+i,   "content"+i));  
  22.         }  
  23.         myAdapter=new MyAdapter(list, this);  
  24.         listView.setAdapter(myAdapter);  
  25.     }  
  26. }  


Custom adapter

MyAdapter.class

  1. package com.example.baseadapter;  
  2.   
  3. import java.util.List;  
  4.   
  5. import android.content.Context;  
  6. import android.util.Log;  
  7. import android.view.View;  
  8. import android.view.ViewGroup;  
  9. import android.widget.BaseAdapter;  
  10. import android.widget.ImageView;  
  11. import android.widget.TextView;  
  12.   
  13. public class MyAdapter extends BaseAdapter {  
  14.   
  15.     private long sum = 0;  
  16.     private List<MyObject> list;  
  17.     private Context context;  
  18.   
  19.     public MyAdapter(List<MyObject> list, Context context) {  
  20.         this.list = list;  
  21.         this.context = context;  
  22.     }  
  23.   
  24.     @Override  
  25.     public int getCount() {  
  26.         // TODO Auto-generated method stub  
  27.         return list.size();  
  28.     }  
  29.   
  30.     @Override  
  31.     public Object getItem(int position) {  
  32.         // TODO Auto-generated method stub  
  33.         return list.get(position);  
  34.     }  
  35.   
  36.     @Override  
  37.     public long getItemId(int position) {  
  38.         // TODO Auto-generated method stub  
  39.         return position;  
  40.     }  
  41.   
  42.     @Override  
  43.     public View getView(int position, View convertView, ViewGroup parent) {  
  44.         // TODO Auto-generated method stub  
  45.         //Comic formula
  46.          long star = System.nanoTime();  
  47.          View view=View.inflate(context, R.layout.item, null);  
  48.          ImageView imageView =(ImageView) view.findViewById(R.id.iv_image);  
  49.          TextView nickName=(TextView) view.findViewById(R.id.tv_nickName);  
  50.          TextView content=(TextView) view.findViewById(R.id.tv_content);  
  51.          MyObject myObject=list.get(position);  
  52.          imageView.setBackgroundResource(myObject.getImageViewId());  
  53.          nickName.setText(myObject.getNickName());  
  54.          content.setText(myObject.getContent());  
  55.          long end = System.nanoTime();  
  56.          sum += end - star;  
  57.          Log.d("main", "Teasing formula" + sum);  
  58.          return view;  
  59.         //(Ordinary)
  60. //long star = System.nanoTime(); // Get system nanosecond time
  61. //      if (convertView == null) {  
  62. //          convertView = View.inflate(context, R.layout.item, null);  
  63. //      }  
  64. //      ImageView imageView = (ImageView) convertView  
  65. //              .findViewById(R.id.iv_image);  
  66. //      TextView nickName = (TextView) convertView  
  67. //              .findViewById(R.id.tv_nickName);  
  68. //      TextView content = (TextView) convertView.findViewById(R.id.tv_content);  
  69. //      MyObject myObject = list.get(position);  
  70. //      imageView.setBackgroundResource(myObject.getImageViewId());  
  71. //      nickName.setText(myObject.getNickName());  
  72. //      content.setText(myObject.getContent());  
  73. //      long end = System.nanoTime();  
  74. //      sum += end - star;  
  75. //Log.d("main", "general"+sum);.
  76. //      return convertView;  
  77.         //Literary and artistic style
  78.         // long star = System.nanoTime();  
  79.         // ViewHolder viewHolder;  
  80.         // if (convertView == null) {  
  81.         // viewHolder=new ViewHolder();  
  82.         // convertView = View.inflate(context, R.layout.item, null);  
  83.         // viewHolder.imageView = (ImageView) convertView  
  84.         // .findViewById(R.id.iv_image);  
  85.         // viewHolder.nickName = (TextView) convertView  
  86.         // .findViewById(R.id.tv_nickName);  
  87.         // viewHolder.content = (TextView) convertView  
  88.         // .findViewById(R.id.tv_content);  
  89.         //// bind viewHolder and convertView together by setTag
  90.         // convertView.setTag(viewHolder);  
  91.         // }  
  92.         // viewHolder=(ViewHolder) convertView.getTag();  
  93.         // MyObject myObject = list.get(position);  
  94.         // viewHolder.imageView.setBackgroundResource(myObject.getImageViewId());  
  95.         // viewHolder.nickName.setText(myObject.getNickName());  
  96.         // viewHolder.content.setText(myObject.getContent());  
  97.         // long end = System.nanoTime();  
  98.         // sum += end - star;  
  99.         //Log.d("main", "literary style"+sum);
  100.         // return convertView;  
  101.     }  
  102.   
  103.     //Avoid duplication of findViewById
  104.     class ViewHolder {  
  105.         public ImageView imageView;  
  106.         private TextView nickName;  
  107.         private TextView content;  
  108.     }  
  109.   
  110. }  


The code of BaseAdapter's triple realm (comma, common, literary) is already above.

Now let's analyse the first kind of funny comparison.

As mentioned earlier, liseview has a caching mechanism to put used item s into the buffer pool, and here we create new view objects every time we call the getview method without using the listview caching mechanism.

There is no treatment, efficiency and inefficiency, so we call it comma.

The second common form is to use the content view object passed in the getview method and add an if judgment.

  1. if (convertView == null) {  
  2.     convertView = View.inflate(context, R.layout.item, null);  
  3. }  

Although it's only an if judgment, it saves a lot of time by avoiding creating a large number of contentview objects. It takes advantage of the caching feature of ListView to create a new view without caching, which optimizes the getview method very well, but it's only an entry point, because findViewById still wastes a lot of time, so we call this method "FindViewById". Ordinary style

Then the third realm literary and artistic form is to optimize findViewById and put findViewById into if judgment statement.

We need to create an internal class with three member variables that are the three controls in our item.xml file.

  1. class ViewHolder {  
  2.     public ImageView imageView;  
  3.     private TextView nickName;  
  4.     private TextView content;  
  5. }  

Connect viewHolder with contentView by viewHolder.setTag() method and get viewHolder by getTag method

This method not only utilizes the cache of listview, but also realizes the cache of display view through viewHolder, avoiding using findViewById method many times.

As a sentimental programmer, this is the most literary way to write.~

You may see the log log output from my code below. I attach the results. Compare the list view here, only 50 pieces of data are all slipped to the bottom.

 

So far, the three realms of BaseAdapter (comic, ordinary, literary) are clear at a glance. (If there are any discrepancies, please set more data in the list view.)

Posted by MsShelle on Mon, 15 Apr 2019 17:12:33 -0700