Appearance
性能、测试、排障
一句话定位
这一模块不是把"性能 / 测试 / 排障"并排罗列,而是按一条问题处理主线建立判断力:
先量化(测量)→ 再归因(定位)→ 后治理(修复)→ 防劣化(CI/APM),测试与排障方法贯穿其中。
读完后,应该能对任意"线上卡顿 / 崩溃 / 启动慢"问题,先判断该用哪类工具、按什么顺序取证,而不是盲试。
模块目标
形成高级工程师级别的性能判断、测试分层、问题定位和跨端排障能力。
本模块要回答的问题
- Android 卡顿 / ANR 的定位路径是什么?
- 一句话答:先看主线程(等锁 /
Future.get()/ Binder / 长任务),再查后台线程池争锁或堆积,用 trace / 线程 dump 定位等待链。
- 一句话答:先看主线程(等锁 /
- Flutter jank / rebuild / isolate 的边界怎么判断?
- 一句话答:jank 看帧耗时;rebuild 看
build频率与范围;isolate 看 CPU 重活是否留在主 isolate;分层测量再定位。
- 一句话答:jank 看帧耗时;rebuild 看
- WebView 性能问题通常卡在哪?
- 一句话答:常卡在 JS 主线程长任务、桥接频繁或数据过大、资源加载与缓存策略、渲染层重绘。
- 单测、widget test、integration test 各自应该承担什么?
- 一句话答:单测验证纯逻辑,widget test 验证组件交互,integration test 验证端到端链路;按成本与覆盖面分层。
- 跨端问题怎么分层缩小范围,而不是乱试?
- 一句话答:按"表现层 → 业务层 → 平台能力层"逐层隔离,先确认复现与边界再定位,避免全栈盲试。
知识导航树:从性能问题到工具链
第一层:性能优化总览(先建立四要素心智)
- 流畅度(FPS / Jank)、启动速度(TTID)、内存与稳定性(OOM / ANR)、资源消耗(包体 / 电量 / 16KB 页)
第二层:专项治理(按问题域深入)
- 启动:冷/温/热启动差异 → 应用启动性能优化实战(拓扑排序、异步初始化与首帧治理) · Android App 进程启动全流程 (Zygote → ActivityThread → 首帧)
- 卡顿:BlockCanary / Perfetto / JankStats → 卡顿监控工具链(Perfetto、Systrace、BlockCanary 与 JankStats)
- 内存:ART GC / Bitmap / 大图 → ART GC 机制、Bitmap 内存演进与大图优化
- Flutter 渲染:Impeller / Shader 编译 → Flutter Impeller 渲染引擎架构与 Shader 编译卡顿消除原理 · Flutter 三棵树与 Layer Tree:Widget / Element / RenderObject / Layer(三棵树 / Layer Tree)
- 包体:瘦身 / AOT 拆包 / 符号化 → Flutter 产物瘦身、AOT 拆包与符号化堆栈还原 (Deobfuscation) · Flutter 编译模式:JIT 与 AOT 的本质差异(JIT/AOT 编译模式,AOT 瘦身的前置因果)
第三层:线上体系(防劣化)
- APM 监控、崩溃率 / ANR 率看板、稳定性治理 → APM 线上性能监控与稳定性体系建设 · Native Crash:Signal、Breakpad 与堆栈还原(Native Crash / Signal / 符号还原)
第四层:测试与排障方法论(贯穿所有专项)
- 测试金字塔分层 → 移动端测试能力总览:单测、Widget/UI 测试与集成测试金字塔
- 排障五步法(现象→复现→数据→定位→验证)→ 系统化排障方法论:现象 → 复现 → 数据 → 定位 → 验证
推荐复习顺序
- 性能优化总览(四要素 + 治理闭环)
- 排障方法论(怎么取证)
- 按业务痛点深入:启动 → 04 · 卡顿 → 05 · 内存 → 08
- 再补线上体系 06 与测试分层 02
- Flutter 渲染深入:11 三棵树/Layer Tree → 09 Impeller;产物与编译看 13 JIT/AOT → 10 瘦身;原生稳定性补 12 Native Crash
对应 labs 入口
已落地实验:
- jank-monitoring-demo —— Choreographer FPS + Looper 卡顿检测
- startup-timing-demo —— 冷启动打点 + adb 测量
- bitmap-memory-demo —— Bitmap Config / inSampleSize / inBitmap / 大图检测 / RegionDecoder
计划补齐:
labs/flutter/performance-testing-debug/—— Flutter rebuild / Impeller 对照实验labs/android/performance-testing-debug/—— ART GC / 内存实验- flutter-three-trees —— Flutter 三树与 Layer 对照(const / RepaintBoundary 实测)
- native-crash-breakpad —— Native Crash / Signal / 符号还原
- flutter-jit-aot —— JIT 与 AOT 产物对照
labs/node/performance-testing-debug/、labs/shared/performance-testing-debug/
复习检查题
为什么性能优化必须"先测量再优化"?
答:现代系统受编译器优化、CPU 调度、缓存层次影响,凭经验猜测往往优化到非瓶颈代码;只有用 Perfetto / Profiler 取基线定位热点,才能精准治理并验证收益。
BlockCanary 为什么能检测主线程卡顿?
答:Looper 在每条消息 Dispatch 前后会调用 Printer;BlockCanary 通过
setMessageLogging拦截前后时间戳,单条消息耗时超过阈值即判定卡顿,并抓取主线程堆栈定位卡点函数。单测、widget test、integration test 为什么按金字塔分层?
答:单测毫秒级、稳定、成本低,适合 70% 的纯逻辑验证;UI 测试秒级中等成本;E2E 分钟级且易受环境波动,只保留关键用户旅程。分层能把验证成本与覆盖面做到最优。
线上偶现 ANR 本地复现不了,第一步该提取什么?
答:提取 ANR 发生瞬间的
/data/anr/traces.txt与主线程堆栈(APM 或 DropBox),确认 main 线程是等锁、Binder 等待还是长任务,再从事实数据出发定位。
备注
这个模块应优先沉淀"问题定位套路"和"真实案例",而不是只写术语。