定义 :
ViewModel是一个数据管理$存储的类
并且是关联生命周期
。feature(特色)
:ViewModel类可让数据在发生屏幕旋转等更改后继续保存。
本文关注的重点问题如下:
什么是数据管理$存储类
为什么需要关联生命周期
上述的feature什么原理
在Activity或者Fragment等具有生命周期的组件上,管理数据会存在什么弊端?
- 当系统因为内存紧缩或者其他原因造成Activity等组件被回收,造成存储在界面的相关数据丢失。Activity可以使用
onSaveInstanceState()
方法从onCreate()
中的参数中恢复界面数据。但此方法适用于可以序列化和反序列化的少量数据,而不适合数量较大的数据,如用户列表或图片等。 - Activity需要大量的通过异步的方式请求数据,同时Activity为了避免内存泄漏,需确保Activity在它销毁的时候清理掉这些调用,这给Activity带来了大量的维护工作。并且Activity在配置发生更改重新创建对象的情况下,会造成资源的浪费,因为Activity可能需要重新发出已发出的调用
- 一般Activity或者Fragment之类的控制器,用于显示界面数据,对用户操作做出响应或处理系统通信等,那么会使类膨胀。以这种方式为Activity或者Fragment分配过多的责任也会大大增加测试的难度。
问题解答:
什么是数据管理,存储类?
百度百科的资料:数据以某种格式记录在计算机内部或外部存储介质上。
对于ViewModel来说,将数据保存到其上,也就是保存到计算机内存中,方便开发者统一管理。减少Activity,Fragment与数据相关的业务代码,有利于测试。有利于数据的统一管理。
为什么需要关联生命周期?
图上解释
:Activity正常的启动,屏幕旋转,最后调用Activity.finish的全过程。图上左边表示对Activity进行的特定操作,图上中间表示发生这些操作时Activity生命周期的变化,图上右边表示ViewModel的生命周期变化,ViewModel Scope表示ViewModel正常运行,clear表示被清除。
问题解释
:为什么需要关联生命周期?因为ViewModel作用的有效的时间范围限定于LifeCycle类上。LifeCycle是关联Activity,Fragment生命周期的,也就是ViewModel需要在Activity,Fragmentfinish
或者detach
时候需要及时释放ViewModel。不释放行不行,不行。因为ViewModel设计的初衷就是为了能让其在Activity和Fragment上共享ViewModel这个对象。而ViewModel与Activity关系应该是一对一的关系,所以不能够在其他Activity上复用,违反使用规则。
上述的feature什么原理
如上图所示,当Activity发生rotated时候,Activity会执行如下的生命周期方法:onPause->onStop->onDestory->onCreate->onStart->onResume方法。一般情况下会在OnCreate方法的参数中恢复一小部分页面数据,其他的需要重新通过异步结果获取。为了避免重复请求异步结果和设置统一路径获取页面数据,才设计出ViewModel类,提供以上的Feature