关于 对lazyload的原理进行的学习
2017-10-23 15:34
344 查看
一、引言
LazyLoad,见文知意,就是懒惰地加载。理念和单例模式中的懒汉模式有异曲同工之处。
在做一个APP的时候,一个ViewPager包含多个Fragment,如果在打开APP的时候每个fragment自动加载,不管是从本地还是网络,都会占用一定的资源。
那我们可以不可以让这个fragment在需要被显示的时候才去加载、初始化呢?
在Fragment中有一个方法——setUserVisibleHint就能实现这个设想。
二、setUserVisibleHint的使用
setUserVisibleHint方法用于告诉系统,这个Fragment的界面对用户当前是否是可见的。所以我们只需要继承Fragment并重写该方法,即可实现在fragment可见时才进行数据加载操作,即Fragment的懒加载。
代码解释:
1.代码开始先设定标志变量isInit代表视图是否已经初初始化,在视图初始化的时候设置为true
标志变量isLoad代表视图是否对用户可见,在视图可见时设为true
2.定义了一个判断是否可以加载数据的方法isCanLoadData() ,*可以加载数据的条件:
* 1.视图已经初始化,isInit==true
* 2.视图对用户可见,getUserVisibleHint()返回true
3.定义了一个lazyLoad的抽象方法,该方法在isCanLoadData()里面调用。起到当视图初始化并且对用户可见的时候去真正的加载数据的作用。
4.定义了一个stopLoad方法,用于在切换到其他页面时停止加载数据。
5.定义方法onDestroyView,视图销毁的时候将Fragment的状态是否初始化变为false。
isInit = false;
isLoad = false;
6.视图是否已经对用户可见,系统的方法setUserVisibleHint(),在其中调用 isCanLoadData方法,实现Fragment数据的缓加载.
代码:
三、注意
isCanLoadData方法也在onCreateView中进行了调用,是因为要进行初始化的工作,毕竟ViewPager是会默认显示第一页的。setUserVisibleHint 的执行顺序又是在 onCreatView 之前,同时 onCreatView 需要初始化界面和修改 isInit 的值。
setUserVisibleHint 的执行顺序是
setUserVisibleHint(false) -> onAttach -> onCreate -> setUserVisibleHint(true) -> onCreateView -> onActivityCreated ->…. -> onDetach参考ITluochen同学的blog
LazyLoad,见文知意,就是懒惰地加载。理念和单例模式中的懒汉模式有异曲同工之处。
在做一个APP的时候,一个ViewPager包含多个Fragment,如果在打开APP的时候每个fragment自动加载,不管是从本地还是网络,都会占用一定的资源。
那我们可以不可以让这个fragment在需要被显示的时候才去加载、初始化呢?
在Fragment中有一个方法——setUserVisibleHint就能实现这个设想。
二、setUserVisibleHint的使用
setUserVisibleHint方法用于告诉系统,这个Fragment的界面对用户当前是否是可见的。所以我们只需要继承Fragment并重写该方法,即可实现在fragment可见时才进行数据加载操作,即Fragment的懒加载。
代码解释:
1.代码开始先设定标志变量isInit代表视图是否已经初初始化,在视图初始化的时候设置为true
标志变量isLoad代表视图是否对用户可见,在视图可见时设为true
2.定义了一个判断是否可以加载数据的方法isCanLoadData() ,*可以加载数据的条件:
* 1.视图已经初始化,isInit==true
* 2.视图对用户可见,getUserVisibleHint()返回true
3.定义了一个lazyLoad的抽象方法,该方法在isCanLoadData()里面调用。起到当视图初始化并且对用户可见的时候去真正的加载数据的作用。
4.定义了一个stopLoad方法,用于在切换到其他页面时停止加载数据。
5.定义方法onDestroyView,视图销毁的时候将Fragment的状态是否初始化变为false。
isInit = false;
isLoad = false;
6.视图是否已经对用户可见,系统的方法setUserVisibleHint(),在其中调用 isCanLoadData方法,实现Fragment数据的缓加载.
代码:
public abstract class LazyLoadFragment extends Fragment { /** * 视图是否已经初初始化 */ protected boolean isInit = false; protected boolean isLoad = false; protected final String TAG = "LazyLoadFragment"; private View view; @Override public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) { view = inflater.inflate(setContentView(), container, false); isInit = true; /**初始化的时候去加载数据**/ isCanLoadData(); return view; } /** * 视图是否已经对用户可见,系统的方法 */ @Override public void setUserVisibleHint(boolean isVisibleToUser) { super.setUserVisibleHint(isVisibleToUser); isCanLoadData(); } /** * 是否可以加载数据 * 可以加载数据的条件: * 1.视图已经初始化 * 2.视图对用户可见 */ private void isCanLoadData() { if (!isInit) { return; } if (getUserVisibleHint()) { lazyLoad(); isLoad = true; } else { if (isLoad) { stopLoad(); } } } /** * 视图销毁的时候讲Fragment是否初始化的状态变为false */ @Override public void onDestroyView() { super.onDestroyView(); isInit = false; isLoad = false; } protected void showToast(String message) { if (!TextUtils.isEmpty(message)) { Toast.makeText(getContext(), message, Toast.LENGTH_SHORT).show(); } } /** * 设置Fragment要显示的布局 * * @return 布局的layoutId */ protected abstract int setContentView(); /** * 获取设置的布局 * * @return */ protected View getContentView() { return view; } /** * 找出对应的控件 * * @param id * @param <T> * @return */ protected <T extends View> T findViewById(int id) { return (T) getContentView().findViewById(id); } /** * 当视图初始化并且对用户可见的时候去真正的加载数据 */ protected abstract void lazyLoad(); /** * 当视图已经对用户不可见并且加载过数据,如果需要在切换到其他页面时停止加载数据,可以覆写此方法 */ protected void stopLoad() { } }
三、注意
isCanLoadData方法也在onCreateView中进行了调用,是因为要进行初始化的工作,毕竟ViewPager是会默认显示第一页的。setUserVisibleHint 的执行顺序又是在 onCreatView 之前,同时 onCreatView 需要初始化界面和修改 isInit 的值。
setUserVisibleHint 的执行顺序是
setUserVisibleHint(false) -> onAttach -> onCreate -> setUserVisibleHint(true) -> onCreateView -> onActivityCreated ->…. -> onDetach参考ITluochen同学的blog
相关文章推荐
- 0909 关于编译原理学习的想法
- 【计算机组成原理系列学习三】关于CPU、指令集、架构以及芯片
- 就C语言的指针、链表的原理和各类操作撰写一篇技术博客,说说自己学习C语言指针和链表的体会,并将学生信息管理系统进行修改,使能完成其他的功能,并撰写体会,附加源代码。
- matlab 关于利用深度学习进行图像识别
- (JAVA SE 学习笔记)Java.SE.第011讲.面向对象之封装.续二(对一些原理机制进行了详细的解释,适合初学者学习)
- 关于绘图 ——学习用origin进行数据的拟合、分析和预测
- oracle rownum用法关于分页,只要看懂了原理,你就明白了,也算是自己学习过程的一个思考
- 学习java接口,关于接口功能的原理
- 【备忘】深度学习实战项目-利用RNN与LSTM网络原理进行唐诗生成视频课程
- QQ通信原理及QQ是怎么穿透内网进行通信的?(关于P2P)
- QQ通信原理及QQ是怎么穿透内网进行通信的?(关于P2P)
- QQ通信原理及QQ是怎么穿透内网进行通信的?(关于P2P)
- 光流算法:关于根据光流(单目)或视差(双目)进行图像变换的原理
- 关于c#连接ftp进行上传下载实现原理及代码
- 一份关于jvm内存调优及原理的学习笔记
- 关于深度学习中的注意力机制,这篇文章从实例到原理都帮你参透了
- 关于学习的游泳的原理
- QQ通信原理及QQ是怎么穿透内网进行通信的?(关于P2P)
- 新年学习进行时:关于十二生肖的英文表达