一文读懂Jetpack LifeCycle的特性和实现

LifeCycle 生命周期

定义

Lifecycle是Jetpack架构组件中用来感知生命周期的组件,目标是使用Lifecycle可以帮助开发者写出与生命周期相关且更简洁、更易维护的代码(不将页面的生命周期透传给对应的组件)-- 监听者模式

使用方式

观察者:LifecycleObserver 和 LifecycleEventObserver

less 复制代码
//无接口,用注解的方式
public interface LifecycleObserver {
}
@OnLifecycleEvent(Lifecycle.Event.ON_DESTROY)


//使用接口的方式,无注解
public interface LifecycleEventObserver extends LifecycleObserver {
void onStateChanged(@NonNull LifecycleOwner source, @NonNull Lifecycle.Event event);
}

宿主:LifeCycleOwner

Fragment,Activity等默认实现了LifeCycleOwner,直接调用getLifeCycle就可以

这里主要讲的是自定义LifeCycleOwner

csharp 复制代码
//暴露的LifecycleOwner接口
public interface LifecycleOwner {
@NonNull
    Lifecycle getLifecycle();
}

//具体的view的实现过程
public Lifecycle getLifecycle() {
    return mLifecycleRegistry; //返回的是注册器
}

//本质这是一个注册器
LifecycleRegistry mLifecycleRegistry;
//注册器和LifeCycleOwner绑定,LifeCycleOwner通过注册器和Observer绑定
mLifecycleRegistry = new LifecycleRegistry(this); //对应的是LifeCycleOwner,但是是弱引用的关系,避免了内存泄漏
//手动更新对应的生命周期(在Activity和Fragment是在源码中实现的)
mLifecycleRegistry.handleLifecycleEvent(Lifecycle.Event.ON_START);

LifecycleRegistry允许手动设置生命周期通知观察者(使用场景是进行单测中手动更新状态)

绑定过程 :LifeCycleOwner绑定Observer

scss 复制代码
//在onCreate生命周期,需要在主线程
lifecycle.addObserver(fragmentLifecycleCallback)
//可以不需要removeObserver,因为在destroy的时候会自动清空

有默认实现LifecycleOwner的场景

  1. 需要首先在基础的地方有实现LifecycleOwner,下面的Activity默认实现了(FragmentActivity、AppCompatActivity以及Fragment都已经实现过了,可以直接使用)
scala 复制代码
public class ComponentActivity extends Activity implements LifecycleOwner
  1. 在基础类的地方增加注册
scss 复制代码
lifecycle.addObserver(advertisingManage)

应用场景

  1. 项目中一些通用的组件,不需要Activity每一个将生命周期都通知给它
  2. 在测试场景中可以通过LifeCycleRegistry mooc一些场景用于测试

优点

  1. 降低组件之间的耦合性,不需要逐层透传

缺点

  1. 灵活性强,不易维护:甚至可以自己既是一个Observer又是一个Owner
kotlin 复制代码
class FeedModel: LifecycleEventObserver, LifecycleOwner {
    constructor(feedRemoteSource: IFeedRemoteSource){
        lifecycleRegistry = LifecycleRegistry(this)
        lifecycleRegistry.currentState = Lifecycle.State.INITIALIZED
lifecycleRegistry.addObserver(this)
    }
    override fun getLifecycle(): Lifecycle {
        return lifecycleRegistry
    }    
}

实现方式

如何实现注册 & 解注册

  1. 在addObserver的时候会立即获得一次生命周期回调的,因为源码中的循环和sync
  2. 在removeObserver的时候不发送额外的销毁DESTROYED事件(避免引入更多的监听者复杂度),因为removeObserver会自动移除
scss 复制代码
public void addObserver(@NonNull LifecycleObserver observer) {
    //必须是主线程注册
    enforceMainThreadIfNeeded("addObserver");  
    
    //根据当前的状态生成一个Observer并更新到对应的状态
    State initialState = mState == DESTROYED ? DESTROYED : INITIALIZED;
    ObserverWithState statefulObserver = new ObserverWithState(observer, initialState);
    
    //将注册的监听器放在FastSafeIterableMap中,这个是LinkedHashMap的简版,允许在遍历的时候更改数据不发生crash(是创建了迭代副本,在遍历的时候按照副本进行遍历)
    ObserverWithState previous = mObserverMap.putIfAbsent(observer, statefulObserver);

    if (previous != null) {
        return;
    }
    LifecycleOwner lifecycleOwner = mLifecycleOwner.get();
    if (lifecycleOwner == null) {
        // it is null we should be destroyed. Fallback quickly
        return;
    }

    boolean isReentrance = mAddingObserverCounter != 0 || mHandlingEvent;
    State targetState = calculateTargetState(observer);
    mAddingObserverCounter++;
    
    //循环遍历上面的View全部状态(循环原因可以后面深究),但是明显
    while ((statefulObserver.mState.compareTo(targetState) < 0
            && mObserverMap.contains(observer))) {
        pushParentState(statefulObserver.mState);
        final Event event = Event.upFrom(statefulObserver.mState);
        if (event == null) {
            throw new IllegalStateException("no event up from " + statefulObserver.mState);
        }
        statefulObserver.dispatchEvent(lifecycleOwner, event);
        popParentState();
        // mState / subling may have been changed recalculate
        targetState = calculateTargetState(observer);
    }

    if (!isReentrance) {
        // we do sync only on the top level.
        sync();
    }
    mAddingObserverCounter--;
}

public void removeObserver(@NonNull LifecycleObserver observer) {
    enforceMainThreadIfNeeded("removeObserver");
    //不发送额外的
    mObserverMap.remove(observer);
}

LifeCycleOwner是如何实现的

Android 10以下Activity本质是通过ReportFragment感知Activity生命周期拦截的(ReportFragment在ComponentActivity中注入的)

scss 复制代码
protected void onCreate(@Nullable Bundle savedInstanceState)
    ReportFragment.injectIfNeededIn(this);
}

public static void injectIfNeededIn(Activity activity) {
    //Android 10以上直接注册生命周期回调
    if (Build.VERSION.SDK_INT >= 29) {
        LifecycleCallbacks.registerIn(activity);
    }
    
    android.app.FragmentManager manager = activity.getFragmentManager();
    if (manager.findFragmentByTag(REPORT_FRAGMENT_TAG) == null) {
        manager.beginTransaction().add(new ReportFragment(), REPORT_FRAGMENT_TAG).commit();
        //立即启动ReportFragment,以达到能够开始接收生命周期事件
        manager.executePendingTransactions();
    }
}

Fragment是通过LifeCycleRegistry实现的

javascript 复制代码
void performCreate(Bundle savedInstanceState) {
   //其中还通过LifeCycleOwner监听实现了:在OnStop生命周期的时候停止接受输入事件
   ....
   mLifecycleRegistry.handleLifecycleEvent(Lifecycle.Event.ON_CREATE);
}

为什么 Android 10 以上不再需要 ReportFragment?

  1. 能节省ReportFragment所占用的资源
  2. 能减少代码的复杂性
相关推荐
Mr数据杨19 分钟前
【Codex】用学生入学评估模块建立新生能力画像
android·java·javascript·django·codex·项目开发
●VON41 分钟前
谁小时候不想要一个游戏修改器?我把电脑 Skill 做成了 Android 小助手
android·游戏·电脑
刃神太酷啦1 小时前
Linux 系统 MySQL 完整安装配置教程:从卸载 MariaDB 到优化 my.cnf----《Hello MySQL!》(1)
android·linux·c语言·c++·mysql·leetcode·mariadb
里欧跑得慢1 小时前
Flutter 三方库 function_tree — 鸿蒙应用开发中的动态数学公式解析与计算神器,实现鸿蒙深度适配下的复杂函数逻辑运行时求值实战(适配鸿蒙 HarmonyOS Next ohos)
android·前端·安全·flutter·华为·harmonyos
IT毕设实战小研1 小时前
基于安卓的空气质量查询系统
android·大数据·vue.js·爬虫·python·django·课程设计
leonkay2 小时前
C# 特性(Attribute)——【1】基础讲解
开发语言·青少年编程·面试·c#·.net·个人开发
leonkay3 小时前
C# 特性(Attribute)——【2】工业设备参数框架设计
经验分享·面试·架构·c#·学习方法·设计
雨声不在4 小时前
docker-android Android 16 支持与编译修改
android
小江的记录本5 小时前
【AI Agent】《2026年9月 AI Agent全栈开发技术选型专项面试宝典》
java·spring boot·python·spring·ai·面试·ai编程
SamDeepThinking6 小时前
里氏替换原则的盲区:为什么符合契约的List替换依然会失败?
后端·面试·程序员