Activity 生命周期是如何被调度的?(从源码到实战全链路拆解)

0 阅读4分钟

一、引言:为什么你需要真正理解生命周期调度?

很多 Android 开发者都“会用”生命周期,但一旦遇到这些问题就容易懵:

  • 为什么 onResume() 有时候没执行?
  • 为什么切后台再回来,Activity 不是从 onCreate() 开始?
  • 为什么在某些机型上会出现 生命周期错乱 / 丢回调
  • Fragment 生命周期为什么“跟着 Activity 但又不完全一样”?

这些问题的本质,其实都指向一个核心:

Activity 生命周期不是“自己执行”的,而是被系统调度的。

如果你不了解调度机制,就无法:

  • Debug 生命周期异常问题
  • 做稳定性优化(ANR / Crash)
  • 做复杂场景(多窗口、冷启动优化)

👉 本文我们就从 系统调度视角,彻底搞懂 Activity 生命周期。


二、背景知识:谁在“控制”Activity?

在 Android 中,Activity 并不是你 new 出来的,而是由系统管理的。

核心参与者有三个:

1. AMS(ActivityManagerService)

👉 系统进程中的“大脑”

职责:

  • 管理 Activity 栈
  • 决定哪个 Activity 该显示
  • 决定生命周期状态(RESUMED / PAUSED 等)

2. ActivityThread(应用进程)

👉 App 主线程的入口

职责:

  • 接收 AMS 指令
  • 分发生命周期回调(onCreate / onResume 等)

3. ApplicationThread(Binder 通道)

👉 AMS 和 App 之间的桥梁

AMS  --(Binder)--> ApplicationThread --(Handler)--> ActivityThread

📌 一句话总结:

AMS 决策,ApplicationThread 传递,ActivityThread 执行。


三、核心原理:生命周期其实是“事务驱动”的

从 Android 9(Pie)开始,生命周期调度引入了一个关键机制:

👉 ClientTransaction(客户端事务模型)


1. 生命周期 ≠ 直接调用

很多人以为:

activity.onResume()

❌ 实际上不是这样调用的!

而是:

AMS → ClientTransaction → ActivityThread → 生命周期方法

2. ClientTransaction 是什么?

可以理解为:

👉 一次完整的生命周期调度“任务包”

它包含:

  • 生命周期状态(Resume / Pause / Stop)
  • Callback(Launch / Destroy / NewIntent 等)

3. 生命周期调度流程(核心链路)

以启动 Activity 为例:

startActivity()
   ↓
AMS(决定启动)
   ↓
ClientTransaction(封装任务)
   ↓
ApplicationThread.scheduleTransaction()
   ↓
ActivityThread.H(Handler)
   ↓
TransactionExecutor.execute()
   ↓
performLaunchActivity()
   ↓
onCreate() / onStart() / onResume()

📌 关键结论:

生命周期不是“一个个方法调用”,而是一组事务执行的结果。


四、源码解析:生命周期到底怎么被调度?

我们来看关键源码路径(基于 Android 10+)


1. AMS 发起调度

clientTransaction.addCallback(LaunchActivityItem.obtain(...));
clientTransaction.setLifecycleStateRequest(
    ResumeActivityItem.obtain(...)
);

👉 重点:

  • Callback:做什么(如 launch)
  • LifecycleState:最终状态(如 RESUMED)

2. 发送到 App 进程

applicationThread.scheduleTransaction(transaction);

3. ActivityThread 接收

public void scheduleTransaction(ClientTransaction transaction) {
    mH.sendMessage(...);
}

👉 切到主线程 Handler


4. TransactionExecutor 执行

executeCallbacks(transaction);
executeLifecycleState(transaction);

5. 执行 launch

performLaunchActivity()

最终调用:

activity.onCreate()
activity.onStart()
activity.onResume()

📌 重点理解:

生命周期是“推导出来的”,而不是“直接指定的”。

比如:

  • 如果目标状态是 RESUMED
  • 当前状态是 INITIAL

系统会自动补齐:

onCreate → onStart → onResume

五、实战示例:生命周期调度可视化

我们写一个简单 Demo,观察生命周期。


示例代码

class MainActivity : AppCompatActivity() {

    private fun log(msg: String) {
        Log.d("LifeCycle", msg)
    }

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        log("onCreate")
    }

    override fun onStart() {
        super.onStart()
        log("onStart")
    }

    override fun onResume() {
        super.onResume()
        log("onResume")
    }

    override fun onPause() {
        super.onPause()
        log("onPause")
    }

    override fun onStop() {
        super.onStop()
        log("onStop")
    }

    override fun onDestroy() {
        super.onDestroy()
        log("onDestroy")
    }
}

场景分析

场景1:启动 Activity

onCreate
onStart
onResume

👉 对应事务:

  • LaunchActivityItem
  • ResumeActivityItem

场景2:打开新 Activity

当前 Activity:
onPause → onStop

新 Activity:
onCreate → onStart → onResume

👉 AMS 做了两件事:

  • Pause 当前 Activity
  • Resume 新 Activity

场景3:按 Home 键

onPause → onStop

👉 目标状态:STOPPED


📌 本质:

生命周期变化 = 状态机迁移


六、常见误区(踩坑重点)

❌ 误区1:生命周期一定按顺序执行?

不一定!

比如异常场景:

  • 进程被杀
  • 配置变更
  • 多窗口模式

👉 可能出现:

  • 没有 onStop() 直接 onDestroy()
  • 或者根本没机会执行

❌ 误区2:onPause 一定比 onResume 先执行?

在多窗口模式下:

👉 多个 Activity 可以同时 RESUMED

(Android 10+ 支持)


❌ 误区3:生命周期回调一定在主线程同步执行?

✔ 在主线程
❌ 不一定是“立即执行”

因为:

它是通过 Handler 异步调度的


❌ 误区4:finish() 一定马上销毁?

finish()

只是发起请求:

👉 实际销毁仍然由 AMS 调度


七、性能优化 & 最佳实践

1. 避免在 onCreate 做重操作

原因:

生命周期调度是串行的,阻塞会影响整个 UI

建议:

lifecycleScope.launch {
    // 异步加载
}

2. 正确使用生命周期感知组件

推荐:

lifecycle.addObserver(...)

或:

repeatOnLifecycle(Lifecycle.State.STARTED) { }

3. 避免生命周期错位问题

典型错误:

onResume {
    registerReceiver()
}

onPause {
    unregisterReceiver()
}

👉 在多窗口下可能出问题

建议:

onStart / onStop

4. 利用 ProcessLifecycleOwner

全局生命周期监听:

ProcessLifecycleOwner.get().lifecycle

适合:

  • App 前后台切换
  • 统计埋点

八、总结:生命周期调度的本质

我们用一句话总结:

Activity 生命周期本质是 AMS 驱动的状态机,通过 ClientTransaction 在主线程中异步执行。


核心记住这 4 点:

  1. 生命周期不是你控制的,是系统调度的
  2. AMS 决策,ActivityThread 执行
  3. ClientTransaction 是调度核心
  4. 生命周期是状态机,而不是简单回调

最后一句

当你真正理解生命周期调度后,你会发现:

很多“玄学 Bug”,其实只是你还没看懂系统的调度逻辑。