一、兩者的緩存機制上的區別
先來說一樣的地方,ListView與RecyclerView緩存機制原理大致一樣,滑動的時候,離開屏幕的ItemView被回收到緩存,新的itemView加在優先獲取的緩存中的,這是正常的兩種類似的緩存機制。
而不同的地方在于,兩者的緩存層級不同,ListView只有兩層,RecycleView有四級緩存。
1. mActiveViews和mAttachedScrap功能相似,意義在于快速重用屏幕上可見的列表項ItemView,而不需要重新createView和bindView;
2. mScrapView和mCachedViews + mReyclerViewPool功能相似,意義在于緩存離開屏幕的ItemView,目的是讓即將進入屏幕的ItemView重用;
3. RecyclerView的優勢在于: a.mCacheViews的使用,可以做到屏幕外的列表項ItemView進入屏幕內時也無須bindView快速重用; b.mRecyclerPool可以供多個RecyclerView共同使用,在特定場景下,如viewpaper+多個列表頁下有優勢.客觀來說,RecyclerView在特定場景下對ListView的緩存機制做了補強和完善。
同時,兩者的緩存不同,RecycleView緩存在ViewHolder,可以看作是:View + ViewHolder(避免每次createView時調用findViewById) + flag(標識狀態);而ListView緩存在View上,獲取緩存的方法流程是:

listView的mScrapViews是根據pos獲取相應的緩存,但不直接用,是重新getView(這樣會重新bindView)。所以ListView中通過pos獲取的是View。
RecycleView的流程是:

mRecycleView在獲取緩存的時候,是通過匹配pos獲得目標的位置的緩存,這么做可以不用重新bindView,所以RecycleVIew中通過pos獲取的是viewholder,是pos-->(view,holder,flag),flag是判斷view是否需要重新bindView。
二、局部刷新的區別
RecycleView中的notifyItemRemoved(position)方法,最終會調用requestLayout()方法,使整個View重新繪制,為:onMeasure()-->onLayout()-->onDraw()
其中的onLayout分三步:
1.dispathLayoutStep1():記錄RecyclerView刷新前列表項ItemView的各種信息,如Top,Left,Bottom,Right,用于動畫的相關計算;
2.dispathLayoutStep2():真正測量布局大小,位置,核心函數為layoutChildren();
3.dispathLayoutStep3():計算布局前后各個ItemView的狀態,如Remove,Add,Move,Update等,如有必要執行相應的動畫.
其中layoutChildren()方法的流程圖:


當調用notifyItemRemoved時,會對屏幕內ItemView做預處理,修改ItemView相應的pos以及flag。當調用fill()中RecyclerView.getViewForPosition(pos)時,RecyclerView通過對pos和flag的預處理,使得bindview只調用一次。
需要指出,ListView和RecyclerView最大的區別在于數據源改變時的緩存的處理邏輯,ListView是"一鍋端",將所有的mActiveViews都移入了二級緩存mScrapViews,而RecyclerView則是更加靈活地對每個View修改標志位,區分是否重新bindView。
以上
新聞熱點
疑難解答