设为首页 加入收藏

TOP

Android开发学习之路-DiffUtil使用教程(一)
2017-10-13 10:35:48 】 浏览:6864
Tags:Android 开发 习之 -DiffUtil 使用 教程

谷歌最近更新了Support Library 24.2.0,而DiffUtil就是在这个版本添加的一个工具类。

DiffUtil是一个查找集合变化的工具类,是搭配RecyclerView一起使用的,如果你还不了解RecyclerView,可以阅读一些资料或者我的博客:RecyclerView使用初探

根据惯例,先放效果图:

可以看到,当我们点击按钮的时候,这个RecyclerView所显示的集合发生了改变,有的元素被增加了(8.Jason),也有的元素被移动了(3.Rose),甚至是被修改了(2.Fndroid)。RecyclerView对于每个Item的动画是以不同方式刷新的:

  • notifyItemInserted
  • notifyItemChanged
  • notifyItemMoved
  • notifyItemRemoved

而对于连续的几个Item的刷新,可以调用:

  • notifyItemRangeChanged
  • notifyItemRangeInserted
  • notifyItemRangeRemoved

而由于集合发生变化的时候,只可以调用notifyDataSetChanged方法进行整个界面的刷新,并不能根据集合的变化为每一个变化的元素添加动画。所以这里就有了DiffUtil来解决这个问题。

DiffUtil的作用,就是找出集合中每一个Item发生的变化,然后对每个变化给予对应的刷新。

这个DiffUtil使用的是Eugene Myers的差别算法,这个算法本身不能检查到元素的移动,也就是移动只能被算作先删除、再增加,而DiffUtil是在算法的结果后再进行一次移动检查。假设在不检测元素移动的情况下,算法的时间复杂度为O(N + D2),而检测元素移动则复杂度为O(N2)。所以,如果集合本身就已经排好序,可以不进行移动的检测提升效率。

 

下面我们一起来看看这个工具怎么用。

首先对于每个Item,数据是一个Student对象:

 1 class Student {
 2     private String name;
 3     private int num;
 4 
 5     public Student(String name, int num) {
 6         this.name = name;
 7         this.num = num;
 8     }
 9 
10     public String getName() {
11         return name;
12     }
13 
14     public void setName(String name) {
15         this.name = name;
16     }
17 
18     public int getNum() {
19         return num;
20     }
21 
22     public void setNum(int num) {
23         this.num = num;
24     }
25 }

接着我们定义布局(省略)和适配器:

 1     class MyAdapter extends RecyclerView.Adapter {
 2         private ArrayList<Student> data;
 3 
 4         ArrayList<Student> getData() {
 5             return data;
 6         }
 7 
 8         void setData(ArrayList<Student> data) {
 9             this.data = new ArrayList<>(data);
10         }
11 
12         @Override
13         public RecyclerView.ViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
14             View itemView = LayoutInflater.from(RecyclerViewActivity.this).inflate(R.layout.itemview, null);
15             return new MyViewHolder(itemView);
16         }
17 
18         @Override
19         public void onBindViewHolder(RecyclerView.ViewHolder holder, int position) {
20             MyViewHolder myViewHolder = (MyViewHolder) holder;
21             Student student = data.get(position);
22             myViewHolder.tv.setText(student.getNum() + "." + student.getName());
23         }
24 
25         @Override
26         public int getItemCount() {
27             return data.size();
28         }
29 
30         class MyViewHolder extends RecyclerView.ViewHolder {
31             TextView tv;
32 
33             MyViewHolder(View itemView) {
34                 super(itemView);
35                 tv = (TextView) itemView.findViewById(R.id.item_tv);
36             }
37         }
38     }

初始化数据集合:

 1     private void initData() {
 2         students = new ArrayList<>();
 3         Student s1 = new Student("John", 1);
 4         Student s2 = new Student("Curry", 2);
 5         Student s3 = new Student("Rose", 3);
 6         Student s4 = new Student("Dante", 4);
 7         Student s5 = new Student("Lunar", 5);
 8         students.add(s1);
 9         students.add(s2);
10         students.add(s3);
11         students.add(s4);
12         students.add(s5);
13     }

接着实例化Adapter并设置给RecyclerView:

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_recycler_view);
        initData();
        recyclerView = (RecyclerView) findViewById(R.id.rv);
        recyclerView.setLayoutManager(new LinearLayoutManager(this));
        adapter = new MyAdapter();
        adapter.setData(students);
        recyclerView.setAdapter(adapter);
    }

这些内容

首页 上一页 1 2 3 下一页 尾页 1/3/3
】【打印繁体】【投稿】【收藏】 【推荐】【举报】【评论】 【关闭】 【返回顶部
上一篇Android快乐贪吃蛇游戏实战项目开.. 下一篇浅析Dagger2的使用

最新文章

热门文章

Hot 文章

Python

C 语言

C++基础

大数据基础

linux编程基础

C/C++面试题目