Android-Jetpack笔记-LiveData
时间:2022-07-23
本文章向大家介绍Android-Jetpack笔记-LiveData,主要内容包括其使用实例、应用技巧、基本知识点总结和需要注意事项,具有一定的参考价值,需要的朋友可以参考一下。
LiveData
即有生命的数据,通过观察者模式实现,当数据发生变化时可以收到回调。同时还具备感知宿主生命周期的能力。
Jetpack笔记代码
本文源码基于SDK 29
使用
引入依赖:
def lifecycle_version = "2.2.0"
//extensions包含Lifecycles、LiveData、ViewModel
implementation "android.arch.lifecycle:extensions:$lifecycle_version"
在act中使用,
class ViewModelActivity extends BaseActivity {
MutableLiveData<String> mLiveData = new MutableLiveData<>();
void onCreate(Bundle savedInstanceState) {
//观察数据变化
mLiveData.observe(this, s -> {
QrLog.e("observe = " + s + "," + getLifecycle().getCurrentState());
});
//设置数据
mLiveData.setValue("onCreate");
}
void onResume() {
//设置数据
mLiveData.setValue("onResume");
}
}
使用起来很简单,下面来看看是怎么实现的。
原理
首先看mLiveData.observe
,
//LiveData.java
public void observe(@NonNull LifecycleOwner owner, @NonNull Observer<? super T> observer) {
//owner是act对象,在Lifecycles中提到过,他可以作为一个被观察者
//observer是观察者
if (owner.getLifecycle().getCurrentState() == DESTROYED) {
return;
}
//包装被观察者和观察者
LifecycleBoundObserver wrapper = new LifecycleBoundObserver(owner, observer);
//存储起来,<观察者,包装类>
ObserverWrapper existing = mObservers.putIfAbsent(observer, wrapper);
//包装类成为act的观察者,能感知act生命周期
owner.getLifecycle().addObserver(wrapper);
}
来到setValue
,
//LiveData.java
protected void setValue(T value) {
//把值记录起来
mData = value;
//开始分发
dispatchingValue(null);
}
void dispatchingValue(@Nullable ObserverWrapper initiator) {
do {
for (Iterator<Map.Entry<Observer<? super T>, ObserverWrapper>> iterator =
mObservers.iteratorWithAdditions(); iterator.hasNext(); ) {
//遍历包装类
considerNotify(iterator.next().getValue());
if (mDispatchInvalidated) {
break;
}
}
} while (mDispatchInvalidated);
}
private void considerNotify(ObserverWrapper observer) {
//从包装类中取出观察者,回调
observer.mObserver.onChanged((T) mData);
}
到这里,流程就已经走完了,值得注意的是,并不是所有生命周期都能观察到值的变化,试着在每个生命周期都setValue一下,会发现只有onStart、onResume、onPause才会收到回调,这是因为,
//LiveData.java
private void considerNotify(ObserverWrapper observer) {
if (!observer.shouldBeActive()) {
//判断是否活跃
observer.activeStateChanged(false);
return;
}
//从包装类中取出观察者,回调
observer.mObserver.onChanged((T) mData);
}
shouldBeActive有两个实现,我们先看这个,
//LiveData.LifecycleBoundObserver
@Override
boolean shouldBeActive() {
//只有getLifecycle().getCurrentState()大于等于STARTED,才通知
return mOwner.getLifecycle().getCurrentState().isAtLeast(STARTED);
}
看下日志,可见只有onStart、onResume、onPause时,getLifecycle().getCurrentState()大于等于STARTED,
再看下另一个实现,
//LiveData.AlwaysActiveObserver
@Override
boolean shouldBeActive() {
//直接返回true
return true;
}
当调用observeForever
时,创建的包装类就是AlwaysActiveObserver
,所以,这时可以在所有生命周期都收到通知,
当然,调用observeForever
的话,由于他的包装类没有进行removeObserver
,需要在业务层手动移除,否则可能会造成内存泄漏,
- observe:包装类是LifecycleBoundObserver(有活跃边界),内部会调removeObserver
- observeForever:包装类是AlwaysActiveObserver (总是活跃),需要手动调removeObserver
优缺点
- 优点:
- 使用简单,可以避免内存泄漏,RxJava则需结合RxLifecycle
- 能感知生命周期,在页面活跃状态才进行通知,可以避免页面不可见时还在占资源
参考文章
- 掘金-Android官方架构组件LiveData: 观察者模式领域二三事
- PHP7新特性介绍
- VFS四大对象之四-struct file
- 《Redis设计与实现》读书笔记(二) ——Redis中的字典(Hash)
- 《Redis设计与实现》读书笔记(三) ——Redis中的链表
- 《Redis设计与实现》读书笔记(四) ——Redis中的跳跃表
- 解析Linux中的VFS文件系统之文件系统的注册(二)
- vivi虚拟摄像头驱动程序
- 系统架构 | 基于微服务架构,改造企业核心系统之实践
- 《Redis设计与实现》读书笔记(五) ——Redis中的整数集合
- 《Redis设计与实现》读书笔记(七) ——Redis对象综述及字符串对象实现原理
- 自动登录脚本
- 极致之处,精彩无限 - 优化了一半的SQL
- 编程修炼 | Scala中Stream的应用场景及其实现原理
- Linux之内存描述符mm_struct
- java教程
- Java快速入门
- Java 开发环境配置
- Java基本语法
- Java 对象和类
- Java 基本数据类型
- Java 变量类型
- Java 修饰符
- Java 运算符
- Java 循环结构
- Java 分支结构
- Java Number类
- Java Character类
- Java String类
- Java StringBuffer和StringBuilder类
- Java 数组
- Java 日期时间
- Java 正则表达式
- Java 方法
- Java 流(Stream)、文件(File)和IO
- Java 异常处理
- Java 继承
- Java 重写(Override)与重载(Overload)
- Java 多态
- Java 抽象类
- Java 封装
- Java 接口
- Java 包(package)
- Java 数据结构
- Java 集合框架
- Java 泛型
- Java 序列化
- Java 网络编程
- Java 发送邮件
- Java 多线程编程
- Java Applet基础
- Java 文档注释
- 容器技术|Docker三剑客之docker-swarm
- 【前端系列-3】layui表格使用自定义模板templet
- 【前端系列-4】layui表格集成select选择框和switch开关
- 使用docker Registry快速搭建私有镜像仓库(内附干货)
- 【前端系列-5】layui-from swtich使用小结
- Python解析变长结构体
- 如何优雅地在JS中使用枚举定义
- 【Java基础-1】 Java8新特性Stream详解
- 【Java基础-2】构造函数与构造代码块
- 【Java基础-3】数据结构之JSON浅析
- linux环境svn服务端及windows环境客户端安装配置
- 【Java集合-1】整体框架
- 【Java集合-2】HashMap简析
- 【Java集合-3】ArrayList简析
- Springboot之Security前后端分离登录