当前位置: 首页 > article >正文

Perfetto 如何查看主线程哪些操作最耗时

在使用 Perfetto 工具时,你可以通过以下步骤定位主线程(Main Thread)上最耗时的操作。Perfetto 提供详细的 CPU 采样和执行轨迹(trace),可以帮助你分析应用性能瓶颈。

1. 捕获 Trace 数据

  • 在 Android Studio 或通过命令行工具,使用 Perfetto 生成一个 trace 文件。在 Android Studio 中,你可以选择 Run > Profiler > Record trace,然后选择 Perfetto 进行记录。确保选择 CPU tracingSystem tracing 以捕获详细的主线程执行数据。

2. 打开 Trace 数据

  • 打开捕获的 trace 文件,使用 Perfetto UI(通过浏览器访问 ui.perfetto.dev),将 trace 文件上传到该界面进行分析。

3. 找到主线程

  • 在 Perfetto UI 界面的时间轴(Timeline)中,你会看到按进程划分的线程列表。
  • 找到应用进程(通常是包含应用包名的进程),然后展开它以找到主线程,通常标记为 Main ThreadUI Thread

4. 分析 Main Thread 的执行情况

  • 任务切片(Slice)查看:主线程上每个执行任务会以“slice”(切片)的形式显示在时间轴上。你可以看到任务的名称和持续时间。
    • 将鼠标悬停在特定的 slice 上,可以查看该任务的执行时间。
    • 红色 slice 通常表示耗时较长的任务,可能是性能问题的来源。

5. 查看调用栈和方法

  • 对于每个 slice,你可以点击它查看详细的调用栈(Call Stack)。这可以帮助你了解具体是哪个方法调用占用了大量时间。
  • 如果捕获了 Java 方法跟踪(Java method tracing),你可以直接查看到主线程上哪些 Java 方法占用了较长时间。这对于分析 UI 渲染、事件处理或后台任务的执行时间非常有帮助。

6. 使用 CPU Profiler

  • Perfetto 的 CPU Profiler 提供了线程切换和 CPU 使用情况的详细信息。你可以查看主线程的 CPU 使用率,并分析线程上下文切换(Context Switch)。
  • 查看主线程的运行状态,找出它是否长时间处于运行态(Running)、等待态(Waiting)或阻塞态(Blocked)。如果长时间处于阻塞状态,则需要查看具体是什么资源在阻塞主线程。

7. 分析长时间的任务

  • 找到那些持续时间较长的任务,分析它们的调用栈和线程状态,特别关注以下常见性能问题:
    • UI 渲染问题:复杂的布局或频繁的 invalidate()requestLayout() 调用可能导致主线程的重绘过多。
    • 事件处理过慢:例如触摸事件、手势识别或点击事件的处理时间过长。
    • 阻塞操作:如长时间的 I/O 操作、网络请求或文件读写,尤其是在主线程上执行的情况下。

8. 使用 Frame Timings(帧时间)分析

  • Perfetto 还会显示每一帧的渲染时间(Frame Timings)。在查看主线程时,可以同时分析每帧的渲染耗时,找出渲染时间超过16ms(导致掉帧)的操作。
  • 查看是否有帧时间明显增加的情况(例如达到 50ms 或更多),然后找到相应的主线程任务,分析它的执行时间。

9. 多维度分析:内存、网络和 I/O 影响

  • 同时结合其他维度的数据,例如内存使用、网络请求、数据库查询等,分析主线程上的操作是否与这些耗时操作有关系。

10. 优化思路

  • 通过上述步骤找到主线程上耗时的操作后,你可以针对性地进行优化。例如:
    • 将耗时的操作(如 I/O 或网络请求)移至后台线程。
    • 优化 UI 渲染,减少不必要的重绘和复杂的布局。
    • 使用异步任务处理长时间执行的操作(如 AsyncTaskExecutorServiceWorkManager)。

总结:

使用 Perfetto,结合时间轴上的主线程 slice,查看调用栈和方法详细信息,可以帮助你定位主线程上的性能瓶颈。重点关注长时间执行的操作,并通过 CPU Profiler 进行线程状态的分析,找出具体的耗时原因,最终针对性地进行优化。


http://www.kler.cn/a/303029.html

相关文章:

  • 算法学习第一弹——C++基础
  • React Hooks在现代前端开发中的应用
  • CTF攻防世界小白刷题自学笔记13
  • STM32问题集
  • 软件测试:测试用例详解
  • acwing算法基础02一高精度,前缀和,差分
  • P1332 血色先锋队
  • 为什么在EffectiveJava中建议用EnumSet替代位字段,以及使用EnumMap替换序数索引
  • layui复选框删除
  • 计算机毕业设计选题推荐-流浪动物领养管理系统-Java/Python项目实战(亮点:数据可视化分析、智能推荐)
  • 开发模式和环境搭建
  • Android 开发避坑经验第三篇:RecyclerView 高效使用与常见问题解决
  • centos下nvme over rdma 环境配置
  • vue原理分析(十二)研究new Vue()中的 initInjections
  • MVVM 基础
  • 计算机科学基础 -- 超流水线
  • cross-plateform 跨平台应用程序-04-React Native 介绍
  • 缓存预热/雪崩/穿透/击穿
  • 基于Python实现一个庆祝中秋节的小程序
  • C#笔记7 网络通信抽象,Socket类的介绍和简单使用
  • 逆向工程 反编译 C# net core
  • 布偶猫应该喂什么猫罐头:交响乐金罐、希喂、尾巴生活测评
  • 复现PointNext代码
  • 【Qt笔记】QGroupBox控件详解
  • 搭建一个大模型API服务
  • 代码随想录打卡Day29