Android性能分析工具 — CPU Profile

目錄

前言

我們都知道个少,應(yīng)用啟動(dòng)慢锥咸、界面切換慢输硝、動(dòng)畫不流暢卡頓等類似問題基本都是UI刷新不及時(shí)的表現(xiàn)绑谣,UI刷新不及時(shí)就是因?yàn)閁I線程被其他邏輯方法長(zhǎng)時(shí)間占用導(dǎo)致党窜。當(dāng)我們著手解決這些性能問題時(shí),面對(duì)的第一個(gè)問題就是需要找到合適的工具來(lái)檢測(cè)這些問題借宵,通過(guò)各項(xiàng)性能指標(biāo)來(lái)進(jìn)行針對(duì)性的優(yōu)化幌衣,這里我們主要講解Android Studio自帶的性能分析工具CPU Profile

本文基于Android Studio 3.2.1版本

CPU Profile簡(jiǎn)介

CPU Profile是 Android 平臺(tái)配備一個(gè)很好的性能分析的工具。它可以通過(guò)圖形化的方式讓我們了解我們要跟蹤的程序的性能暇务,并且能具體到 method泼掠,它可以加載 trace 文件,用圖形的形式展示代碼的執(zhí)行時(shí)間垦细、次數(shù)調(diào)用棧择镇,便于我們分析,幫助我們最大限度減少應(yīng)用的 CPU 使用率

trace 文件是 log 信息文件的一種括改,可以通過(guò)Debug類生成

生成Trace文件

1.通過(guò)代碼生成

public void fun() {
      //開始trace腻豌,保存文件到 /sdcard/funTrace.trace
    Debug.startMethodTracing("funTrace");
    //想要監(jiān)測(cè)的代碼
    ....
    //結(jié)束trace
    Debug.stopMethodTracing();
}

第一步:通過(guò)Debug.startMethodTracing("funTrace");開始產(chǎn)生trace數(shù)據(jù),通過(guò) Debug.stopMethodTracing();結(jié)束監(jiān)測(cè),生成trace文件(如果系統(tǒng)達(dá)到最大緩存大小時(shí)吝梅,還沒有調(diào)用stopMethodTracing()虱疏,系統(tǒng)會(huì)停止跟蹤并發(fā)送一個(gè)通知)

第二步:通過(guò)adb命令 adb pull /sdcard/funTrace.trace /Users/geekholt/Downloadstrace文件導(dǎo)出到電腦

第三步:將trace文件直接拖到Android Studio中進(jìn)行分析

通過(guò)代碼生成trace文件更容易控制開始點(diǎn)和結(jié)束點(diǎn),且可以導(dǎo)出trace文件苏携。但是這種方式運(yùn)行時(shí)開銷嚴(yán)重做瞪,程序方法執(zhí)行整體都會(huì)變慢,可能會(huì)帶偏優(yōu)化方向

traceview is deprecated.png

traceview官方文檔

  1. 使用CPU Profile

第一步:點(diǎn)擊Android studio工具欄中的Profile右冻,運(yùn)行項(xiàng)目

profile.png

第二步:選擇CPU Profile装蓬,點(diǎn)擊Record開始記錄,相當(dāng)于執(zhí)行代碼Debug.startMethodTracing();,再點(diǎn)一次停止記錄,相當(dāng)于執(zhí)行代碼 Debug.stopMethodTracing();伍伤,這樣就生成了trace文件

第三步:生成trace文件后,Android Studio會(huì)自動(dòng)加載trace文件暗赶,并展示圖形化界面

Trace文件分析

默認(rèn)視圖分析

當(dāng)您打開 CPU Profiler 時(shí),它將立即開始顯示應(yīng)用的 CPU 使用率和線程 Activity肃叶。 您應(yīng)該會(huì)看到類似圖 1 的一些內(nèi)容:

圖 1. CPU Profiler.png

如圖 1 所示蹂随,CPU Profiler 的默認(rèn)視圖包括以下內(nèi)容:

  1. Event 時(shí)間線: 顯示應(yīng)用中在其生命周期不同狀態(tài)間轉(zhuǎn)換的 Activity,并表明用戶與設(shè)備的交互被环,包括屏幕旋轉(zhuǎn) Event

  2. CPU 時(shí)間線: 顯示應(yīng)用的實(shí)時(shí) CPU 使用率(以占總可用 CPU 時(shí)間的百分比表示)以及應(yīng)用使用的總線程數(shù)糙及。 此時(shí)間線還顯示其他進(jìn)程的 CPU 使用率(如系統(tǒng)進(jìn)程或其他應(yīng)用),以便您可以將其與您的應(yīng)用使用率進(jìn)行對(duì)比筛欢。 通過(guò)沿時(shí)間線的水平軸移動(dòng)鼠標(biāo)浸锨,您還可以檢查歷史 CPU 使用率數(shù)據(jù)

  3. 線程 Activity 時(shí)間線

    列出屬于應(yīng)用進(jìn)程的每個(gè)線程并使用下面列出的顏色沿時(shí)間線標(biāo)示它們的 Activity。 在您記錄一個(gè)函數(shù)跟蹤后版姑,您可以從此時(shí)間線中選擇一個(gè)線程以在跟蹤窗格中檢查其數(shù)據(jù)

    • 綠色: 表示線程處于活動(dòng)狀態(tài)或準(zhǔn)備使用 CPU柱搜。 即,它正在“運(yùn)行中”或處于“可運(yùn)行”狀態(tài)

    • 黃色: 表示線程處于活動(dòng)狀態(tài)剥险,但它正在等待一個(gè) I/O 操作(如磁盤或網(wǎng)絡(luò) I/O)聪蘸,然后才能完成它的工作

    • 灰色: 表示線程正在休眠且沒有消耗任何 CPU 時(shí)間。 當(dāng)線程需要訪問尚不可用的資源時(shí)偶爾會(huì)發(fā)生這種情況表制。 線程進(jìn)入自主休眠或內(nèi)核將此線程置于休眠狀態(tài)健爬,直到所需的資源可用

trace文件視圖分析

圖 2. 記錄函數(shù)跟蹤后的 CPU Profiler
  1. 選擇時(shí)間范圍: 用于確定您要在跟蹤窗格中檢查所記錄時(shí)間范圍的哪一部分。 當(dāng)您首次記錄函數(shù)跟蹤時(shí)么介,CPU Profiler 將在 CPU 時(shí)間線中自動(dòng)選擇您的記錄的完整長(zhǎng)度娜遵。 如果您想僅檢查所記錄時(shí)間范圍一小部分的函數(shù)跟蹤數(shù)據(jù),您可以點(diǎn)擊并拖動(dòng)突出顯示的區(qū)域邊緣以修改其長(zhǎng)度
  2. 時(shí)間戳: 用于表示所記錄函數(shù)跟蹤的開始和結(jié)束時(shí)間(相對(duì)于分析器從設(shè)備開始收集 CPU 使用率信息的時(shí)間)壤短。 在選擇時(shí)間范圍時(shí)慨仿,您可以點(diǎn)擊時(shí)間戳以自動(dòng)選擇完整記錄,如果您有多個(gè)要進(jìn)行切換的記錄镰吆,則此做法尤其有用
  3. 跟蹤窗格: 用于顯示您所選的時(shí)間范圍和線程的函數(shù)跟蹤數(shù)據(jù)跑慕。 僅在您至少記錄一個(gè)函數(shù)跟蹤后此窗格才會(huì)顯示。 在此窗格中核行,您可以選擇想如何查看每個(gè)堆疊追蹤(使用跟蹤標(biāo)簽),以及如何測(cè)量執(zhí)行時(shí)間(使用時(shí)間引用下拉菜單)
  4. 選擇后,可通過(guò) Top Down 樹婆赠、Bottom Up 樹、調(diào)用圖表火焰圖的形式顯示您的函數(shù)跟蹤休里。 您可以在下文中了解每個(gè)跟蹤窗格標(biāo)簽的更多信息
  5. 從下拉菜單中選擇以下選項(xiàng)之一,以確定如何測(cè)量每個(gè)函數(shù)調(diào)用的時(shí)間信息:
    • Wall clock time:壁鐘時(shí)間信息表示實(shí)際經(jīng)過(guò)的時(shí)間
    • Thread time:線程時(shí)間信息表示實(shí)際經(jīng)過(guò)的時(shí)間減去線程沒有消耗 CPU 資源的任意時(shí)間部分悴侵。 對(duì)于任何給定函數(shù)拭嫁,其線程時(shí)間始終少于或等于其壁鐘時(shí)間。 使用線程時(shí)間可以讓您更好地了解線程的實(shí)際 CPU 使用率中有多少是給定函數(shù)消耗的

使用 Call Chart 標(biāo)簽檢查跟蹤

Call Chart 標(biāo)簽提供函數(shù)跟蹤的圖形表示形式做粤,其中,水平軸表示函數(shù)調(diào)用(或調(diào)用方)的時(shí)間段和時(shí)間妇垢,并沿垂直軸顯示其被調(diào)用者。 對(duì)系統(tǒng) API 的函數(shù)調(diào)用顯示為橙色闯估,對(duì)應(yīng)用自有函數(shù)的調(diào)用顯示為綠色吼和,對(duì)第三方 API(包括 Java 語(yǔ)言 API)的函數(shù)調(diào)用顯示為藍(lán)色。 下面的圖 3 展示了一個(gè)調(diào)用圖表示例尤辱,并描繪了給定函數(shù)的 self time砂豌、children time 以及總時(shí)間的概念

圖 3. 一個(gè)調(diào)用圖表示例阳距,描繪了函數(shù) D 的 self结借、children 及總時(shí)間

提示: 若要跳轉(zhuǎn)到某個(gè)函數(shù)的源代碼,請(qǐng)右鍵點(diǎn)擊該函數(shù)并選擇 Jump to Source

使用 Flame Chart 標(biāo)簽檢查跟蹤

Flame Chart 標(biāo)簽提供一個(gè)倒置的調(diào)用圖表咖熟,其匯總相同的調(diào)用堆棧。 即馍管,收集共享相同調(diào)用方順序的完全相同的函數(shù)薪韩,并在火焰圖中用一個(gè)較長(zhǎng)的橫條表示它們(而不是將它們顯示為多個(gè)較短的橫條,如調(diào)用圖表中所示)俘陷。 這樣更方便您查看哪些函數(shù)消耗最多時(shí)間。 不過(guò)桨菜,這也意味著水平軸不再代表時(shí)間線捉偏,相反,它表示每個(gè)函數(shù)相對(duì)的執(zhí)行時(shí)間

為幫助說(shuō)明此概念告私,請(qǐng)考慮以下圖 4 中的調(diào)用圖表。 請(qǐng)注意驻粟,函數(shù) D 多次調(diào)用 B(B1根悼、B2 和 B3)挤巡,其中一些對(duì) B 的調(diào)用也調(diào)用了 C(C1 和 C3)

圖 4. 包含多個(gè)共享通用調(diào)用方順序的函數(shù)調(diào)用的調(diào)用圖表

由于 B1酷麦、B2 和 B3 共享相同的調(diào)用方順序 (A → D → B),因此沃饶,可將它們匯總在一起轻黑,如下所示氓鄙。 同樣,將 C1 和 C3 匯總在一起抖拦,因?yàn)樗鼈円补蚕硐嗤恼{(diào)用方順序 (A → D → B → C)—請(qǐng)注意舷暮,未包含 C2,因?yàn)樗哂胁煌恼{(diào)用方順序 (A → D → C)

圖 5. 匯總共享相同調(diào)用堆棧的相同函數(shù)

匯總的函數(shù)調(diào)用用于創(chuàng)建火焰圖下面,如圖 6 所示。請(qǐng)注意沥割,對(duì)于火焰圖中任何給定的函數(shù)調(diào)用,消耗最多 CPU 時(shí)間的被調(diào)用方首先顯示

使用 Top Down 和 Bottom Up 檢查跟蹤

Top Down 標(biāo)簽顯示一個(gè)函數(shù)調(diào)用列表,在該列表中展開函數(shù)節(jié)點(diǎn)會(huì)顯示函數(shù)的被調(diào)用方蓄髓。 圖 7 顯示圖 3 中調(diào)用圖表的“Top Down”圖表。圖表中的每個(gè)箭頭都從調(diào)用方指向被調(diào)用方

如圖 7 所示会喝,在“Top Down”標(biāo)簽中展開函數(shù) A 的節(jié)點(diǎn)可顯示它的被調(diào)用方,即函數(shù) B 和 D肢执。 然后,展開函數(shù) D 的節(jié)點(diǎn)可顯示它的被調(diào)用方预茄,即函數(shù) B 和 C 等等。 與 Flame chart 標(biāo)簽相似耻陕,“Top Down”樹匯總共享相同調(diào)用堆棧的相同函數(shù)的跟蹤信息。 也就是說(shuō)膘怕,Flame chart 標(biāo)簽可提供Top down 標(biāo)簽的圖形化表示形式

Top Down 標(biāo)簽提供以下信息以幫助說(shuō)明在每個(gè)函數(shù)調(diào)用上所花費(fèi)的 CPU 時(shí)間(時(shí)間也可以用線程總時(shí)間占所選時(shí)間范圍的持續(xù)時(shí)間的百分比表示):

  • Self: 表示函數(shù)調(diào)用在執(zhí)行自己的代碼(而非被調(diào)用方的代碼)上所花的時(shí)間召庞,如圖 3 中的函數(shù) D 所示
  • Children: 表示函數(shù)調(diào)用在執(zhí)行自己的被調(diào)用方(而非自己的代碼)上所花的時(shí)間来破,如圖 3 中的函數(shù) D 所示
  • 總和: 函數(shù)的 SelfChildren 時(shí)間的總和。 這表示應(yīng)用在執(zhí)行函數(shù)調(diào)用上所花的總時(shí)間徘禁,如圖 3 中函數(shù) D 所示
圖 7. “Top Down”樹和“Bottom Up”樹

Bottom Up 標(biāo)簽顯示一個(gè)函數(shù)調(diào)用列表晌坤,在該列表中展開函數(shù)節(jié)點(diǎn)將顯示函數(shù)的調(diào)用方。 通過(guò)使用圖 7 中展示的跟蹤示例骤菠,圖 7 為函數(shù) C 的Bottom Up”樹疤孕。 在“Bottom Up”樹中打開函數(shù) C 的節(jié)點(diǎn)可顯示它獨(dú)有的調(diào)用方,即函數(shù) B 和 D祭阀。 請(qǐng)注意鹉戚,盡管 B 調(diào)用 C 兩次专控,但在“Bottom Up”樹中展開函數(shù) C 的節(jié)點(diǎn)時(shí),B 僅顯示一次伦腐。 然后,展開 B 的節(jié)點(diǎn)顯示其調(diào)用方幸冻,即函數(shù) A 和 D

Bottom Up 標(biāo)簽用于按照消耗最多(最少)CPU 時(shí)間排序函數(shù)咳焚。 您可以檢查每個(gè)節(jié)點(diǎn)以確定在調(diào)用函數(shù)上哪些調(diào)用方花了最多 CPU 時(shí)間洽损。 與“Top Down”樹相比碑定,“Bottom Up”樹中的每個(gè)函數(shù)的時(shí)間信息引用每個(gè)樹頂部的函數(shù)(頂部模式)又官。 CPU 時(shí)間也可表示為在該記錄期間占線程總時(shí)間的百分比。 下表有助于闡述如何解釋頂部節(jié)點(diǎn)的時(shí)間信息及其調(diào)用方函數(shù)(子節(jié)點(diǎn))

Self Children 合計(jì)
“Bottom Up”樹頂部的函數(shù)(頂部模式) 表示函數(shù)在執(zhí)行自己的代碼(而非其被調(diào)用方的代碼)上所花的時(shí)間赏胚。 與“Top Down”樹相比,此時(shí)間信息表示在記錄的持續(xù)時(shí)間內(nèi)對(duì)此函數(shù)所有調(diào)用的總和崖疤。 表示函數(shù)執(zhí)行它的被調(diào)用方(而非它自己的代碼)上所花的總時(shí)間。 與“Top Down”樹相比劫哼,此時(shí)間信息表示在記錄的持續(xù)期間內(nèi)所有對(duì)此函數(shù)被調(diào)用方的調(diào)用總和。 self time 和 children time 的總和权烧。
調(diào)用方函數(shù)(子節(jié)點(diǎn)) 表示在由調(diào)用方調(diào)用時(shí)被調(diào)用方的總 self time。 以圖 7 中的“Bottom Up”樹為例妻率,被 B 調(diào)用時(shí)板祝,函數(shù) B 的 self time 將等于函數(shù) C 每個(gè)執(zhí)行的 self time 的總和。 表示在由調(diào)用方調(diào)用時(shí)被調(diào)用方的總 children time券时。 以圖 7 中的“Bottom Up”樹為例,被 B 調(diào)用時(shí)橘洞,函數(shù) B 的 children time 將等于函數(shù) C 每個(gè)執(zhí)行的 children time 的總和。 self time 和 children time 的總和炸枣。
最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末,一起剝皮案震驚了整個(gè)濱河市,隨后出現(xiàn)的幾起案子套才,更是在濱河造成了極大的恐慌,老刑警劉巖背伴,帶你破解...
    沈念sama閱讀 217,406評(píng)論 6 503
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現(xiàn)場(chǎng)離奇詭異傻寂,居然都是意外死亡,警方通過(guò)查閱死者的電腦和手機(jī)疾掰,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 92,732評(píng)論 3 393
  • 文/潘曉璐 我一進(jìn)店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來(lái)静檬,“玉大人并级,你說(shuō)我怎么就攤上這事嘲碧「缸瑁” “怎么了?”我有些...
    開封第一講書人閱讀 163,711評(píng)論 0 353
  • 文/不壞的土叔 我叫張陵加矛,是天一觀的道長(zhǎng)。 經(jīng)常有香客問我荒椭,道長(zhǎng),這世上最難降的妖魔是什么狸棍? 我笑而不...
    開封第一講書人閱讀 58,380評(píng)論 1 293
  • 正文 為了忘掉前任味悄,我火速辦了婚禮,結(jié)果婚禮上唐片,老公的妹妹穿的比我還像新娘。我一直安慰自己费韭,他們只是感情好庭瑰,可當(dāng)我...
    茶點(diǎn)故事閱讀 67,432評(píng)論 6 392
  • 文/花漫 我一把揭開白布弹灭。 她就那樣靜靜地躺著,像睡著了一般穷吮。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上八回,一...
    開封第一講書人閱讀 51,301評(píng)論 1 301
  • 那天,我揣著相機(jī)與錄音伟墙,去河邊找鬼滴铅。 笑死,一個(gè)胖子當(dāng)著我的面吹牛汉匙,可吹牛的內(nèi)容都是我干的。 我是一名探鬼主播戏自,決...
    沈念sama閱讀 40,145評(píng)論 3 418
  • 文/蒼蘭香墨 我猛地睜開眼伤锚,長(zhǎng)吁一口氣:“原來(lái)是場(chǎng)噩夢(mèng)啊……” “哼!你這毒婦竟也來(lái)了猛们?” 一聲冷哼從身側(cè)響起狞洋,我...
    開封第一講書人閱讀 39,008評(píng)論 0 276
  • 序言:老撾萬(wàn)榮一對(duì)情侶失蹤,失蹤者是張志新(化名)和其女友劉穎吉懊,沒想到半個(gè)月后,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體态鳖,經(jīng)...
    沈念sama閱讀 45,443評(píng)論 1 314
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡恶导,尸身上長(zhǎng)有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 37,649評(píng)論 3 334
  • 正文 我和宋清朗相戀三年,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片羽戒。...
    茶點(diǎn)故事閱讀 39,795評(píng)論 1 347
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡,死狀恐怖缸废,靈堂內(nèi)的尸體忽然破棺而出,到底是詐尸還是另有隱情企量,我是刑警寧澤,帶...
    沈念sama閱讀 35,501評(píng)論 5 345
  • 正文 年R本政府宣布硅瞧,位于F島的核電站,受9級(jí)特大地震影響腕唧,放射性物質(zhì)發(fā)生泄漏瘾英。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,119評(píng)論 3 328
  • 文/蒙蒙 一但惶、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧膀曾,春花似錦煌集、人聲如沸。這莊子的主人今日做“春日...
    開封第一講書人閱讀 31,731評(píng)論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽(yáng)喊废。三九已至,卻和暖如春污筷,著一層夾襖步出監(jiān)牢的瞬間,已是汗流浹背瓣蛀。 一陣腳步聲響...
    開封第一講書人閱讀 32,865評(píng)論 1 269
  • 我被黑心中介騙來(lái)泰國(guó)打工惋增, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留,地道東北人诈皿。 一個(gè)月前我還...
    沈念sama閱讀 47,899評(píng)論 2 370
  • 正文 我出身青樓,卻偏偏與公主長(zhǎng)得像稽亏,于是被迫代替她去往敵國(guó)和親。 傳聞我的和親對(duì)象是個(gè)殘疾皇子截歉,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 44,724評(píng)論 2 354