带有动画的Android Recycler视图适配器过滤器

Har*_*ani 7 android android-filterable recycler-adapter android-recyclerview

我正在尝试优化Android中的RecyclerView Adapter的过滤方法.该列表用作ArrayList.我看过这篇文章但他们每次都会从原始列表中过滤掉.

示例:如果字符串'a'有10个结果,则用户输入'm','am'结果是'a'结果的子集(results.size()<= 10).

我在这个问题上有三点要问,

  1. 我可以使用ArrayMap优化HashMap内存吗?我应该在String中使用逗号分隔位置而不是Integer对象数组或使用int原始数组的任何方式吗?
  2. 我没有在这个结果中得到任何动画,如何得到它?(我notifyItemInserted还在使用动画)
  3. 在Hashmap中应该保留多少数据,直到2个字符或者应该根据结果列表大小?
我很高兴知道除了这些要点之外,在这个代码中是否可以做得更好.

在下面的代码中,mList用于onBindViewHolder方法中.copyList始终包含所有数据(不对其进行插入或删除).

class MyFilter extends Filter {


        /**
         * 1. check do we have search results available (check map has this key)
         * 2. if available, remove all rows and add only those which are value for that key (string)
         * 3. else check do we have any key available starting like this, s=har, already available -ha then it can be reused
         *
         * @param constraint
         */
        @Override
        protected FilterResults performFiltering(CharSequence constraint) {
            //Here you have to implement filtering way
            final FilterResults results = new FilterResults();

            if (!mSearchMap.containsKey(constraint.toString())) {
                String supersetKey = getSupersetIfAvailable(mSearchMap, constraint.toString());
                if (supersetKey == null) {
                    List<Integer> foundPositions = doFullSearch(copyList, constraint.toString());
                    mSearchMap.put(constraint.toString(), foundPositions);
                } else {
                    List<Integer> foundPositions = filterFromSuperset(copyList, mSearchMap.get(supersetKey), constraint.toString());
                    mSearchMap.put(constraint.toString(), foundPositions);
                }
            }


            return results;
        }

        private String getSupersetIfAvailable(Map<String, List<Integer>> mSearchMap, String s) {
            Set<String> set = mSearchMap.keySet();
            List<String> list = new ArrayList<>(set);
            Collections.sort(list);
            Collections.reverse(list);
            for (String c : list) {
                if (s.startsWith(c)) {
                    return c;
                }
            }
            return null;
        }
        private List<Integer> filterFromSuperset(List<WeekWorkBean> list, List<Integer> supersetResults, String s) {
            List<Integer> results = new ArrayList<>();
            String lowerS = s.toLowerCase();
            for (int i = 0; i < supersetResults.size(); i++) {
                if (list.get(supersetResults.get(i)).getEmpName().toLowerCase().startsWith(lowerS)) {
                    results.add(supersetResults.get(i));
                }
            }
            return results;
        }

        private List<Integer> doFullSearch(List<WeekWorkBean> list, String s) {
            List<Integer> results = new ArrayList<>();
            for (int i = 0; i < list.size(); i++) {
                if (list.get(i).getEmpName().toLowerCase().startsWith(s.toLowerCase())) {
                    results.add(i);
                }
            }
            return results;
        }

        @Override
        protected void publishResults(CharSequence constraint, FilterResults results) {
            // here you can use result - (f.e. set in in adapter list)
            mList.clear();
            notifyDataSetChanged();
            List<Integer> res = mSearchMap.get(constraint.toString());
            int j = 0;
            for (Integer i : res) {
                mList.add(copyList.get(i));
                notifyItemInserted(j++);
            }
        }
    }
Run Code Online (Sandbox Code Playgroud)

woj*_*ski 4

看看这个 https://medium.com/@iammert/using-diffutil-in-android-recyclerview-bdca8e4fbb00#.ehc0gaijt

DiffUtils 正是您所寻找的。您可以在 Rx 链中使用它,将其移出 mainThread 以获取大量数据。这是一个示例 https://medium.com/@nullthemall/diffutil-is-a-must-797502bc1149#.yg35y9q9b