遊戲陪玩app原始碼開發,啟動速度優化與監控

雲豹科技程式設計師發表於2021-09-27

在遊戲陪玩app原始碼開發過程中發現,市場上這類軟體都是大同小異。為了能讓產品比競品更具競爭力,做為開發者,除了完成來自產品經理需求外,我們能做的還有這些:

  • 崩潰率優化
  • 互動的優化
  • 動畫的優化

我把遊戲陪玩app原始碼啟動速度的優化歸結在互動優化中
一般情況下,遊戲陪玩app原始碼的啟動分為冷啟動和熱啟動

  • 冷啟動
    遊戲陪玩app原始碼啟動前,它的程式不在系統裡,需要系統新建立一個程式分配給他啟動的情況,即遊戲陪玩app原始碼從被殺死的情況下啟動
  • 熱啟動
    遊戲陪玩app原始碼在冷啟動後將程式退到後臺,在遊戲陪玩app原始碼程式還在系統裡的情況下,使用者重 新啟動進入遊戲陪玩app原始碼的過程,即遊戲陪玩app原始碼從被掛起的情況下啟動,這個過程做的事情非常少

這篇文章主要探討遊戲陪玩app原始碼冷啟動的優化

使用者能感知到的啟動慢,其實都發生在主執行緒上,而主執行緒慢的原因有很多,比如在主執行緒上執行了大檔案讀寫操作、在渲染週期執行了大量計算等。但是,有時候你會發現即使你把首屏顯示之前的這些主執行緒的耗時問題都解決了,還是比競品啟動得慢。

一般而言,遊戲陪玩app原始碼的啟動時間,指的是從使用者點選遊戲陪玩app原始碼開始,到使用者看到第一個介面之間的時間,總結來說,遊戲陪玩app原始碼的啟動主要包括三個階段:

  1. main()函式執行前
  2. main()函式執行後
  3. 首屏渲染完成後

main()函式執行前

在 main()函式執行前,遊戲陪玩app原始碼主要會做下面幾件事:

  • 載入可執行檔案(遊戲陪玩app原始碼的.o檔案的集合)
  • 載入動態連結庫,進行rebase指標調整和bind符號繫結
  • objc 執行時的初始處理,包括objc相關類的註冊、category註冊、selector唯一性檢查等
  • 初始化,包括了執行+load()方法、attribute((constructor))修飾的函式的呼叫、建立C++靜態全域性變數

相應的,在這個階段對於啟動速度優化來說,可以做的事情包括:

  • 減少動態庫載入,每個庫本身都有依賴關係,蘋果官方建議使用更少的動態庫,並且建議在使用動態庫的數量較多時,儘量將多個動態庫進行合併。數量上,蘋果公司最多可以支援6個非系統動態庫合併為1個
  • 減少載入啟動後不會去使用的類或者方法
  • +load()方法裡的內容可以放到首屏渲染完成後再執行,或使用+initialize方法替換掉。因為,在一個+load()方法裡,執行執行時方法替換操作會帶來4毫秒的消耗,不要小看這4毫秒,積少成多,執行+load()方法對啟動速度的影響會越來越大
  • 控制C++全域性變數的數量

main()函式執行後

main()函式執行後的階段,指的是從main() 函式執行開始,到 appDelegate的(BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {}方法裡首屏渲染相關方法執行完成
首頁的業務程式碼都是要在這個階段,也就是首屏渲染前執行的,主要包括了:

  • 遊戲陪玩app原始碼首屏初始化所需配置檔案的讀寫操作
  • 首屏列表大資料的讀取
  • 遊戲陪玩app原始碼首屏渲染的大量計算等

很多時候,我們會把各種初始化工作都放到這個階段執行(如各類sdk初始化),導致渲染完成置後。更加優化的開發方式,應該是從功能上梳理出哪些是首屏渲染必要的初始化功能,哪些是遊戲陪玩app原始碼啟動必要的初始化功能,而哪些是隻需要在對應功能開始使用時才需要初始化的。梳理完之後,將這些初始化功能分別放到合適的階段進行。

首屏顯示完成後

首屏渲染完成後的這個階段,主要完成的是,遊戲陪玩app原始碼非首屏其它業務服務模組的初始化、監聽的註冊、配置檔案的讀取等。從函式上來看,這個階段指的就是截止到(BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {}方法作用域內執行首屏渲染之後的所有執行方法。簡單說的話,這個階段就是從渲染完成時,到(BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {}方法作用域結束時結束。
這個階段使用者已經能夠看到遊戲陪玩app原始碼的首頁資訊了,所以優化的優先順序排在最後。但是,那些會卡住主執行緒的方法還是需要最優先處理的,不然還是會影響到使用者後面的互動操作。

明白了遊戲陪玩app原始碼啟動階段需要完成的工作後,我們就可以有的放矢的進行啟動速度的優化了。這些優化,包括了功能級別和方法級別的優化

功能級別的啟動優化

遊戲陪玩app原始碼功能級別的啟動優化,就是要從main()函式執行後這個階段入手
優化的思路是:main()函式開始執行後到首屏渲染完成前只處理首屏相關的業務,其他非首屏業務的初始化、監聽註冊、配置檔案讀取等都放到首屏渲染完成後去做

方法級別的啟動優化

經過功能級別的啟動優化,也就是將首屏業務所需的功能滯後以後,當使用者點選遊戲陪玩app原始碼到看到首屏的時間將會很大程度的縮減,也就達到了優化遊戲陪玩app原始碼啟動速度的目的。
在這之後,我們需要進一步做的,是堅持首屏渲染完成前主執行緒上有哪些耗時方法,將沒必要的耗時方法滯後或者非同步執行。通常情況下,耗時較長的方法主要發生在計算大量資料的情況下,具體的表現就是載入、編輯、儲存圖片和檔案等資源

遊戲陪玩app原始碼啟動速度的監控

  • 定時抓取主執行緒上的方法呼叫堆疊,計算一段時間裡各個方法的耗時。Xcode工具裡的Time Profile 採用的就是這種方式
  • 對objc_msgSend 方法進行hook來掌握所有方法的執行耗時

hook方法的意思是,在原方法開始執行時換成其他你指定的方法,或者再原有方法執行前後執行你指定的方法,來達到掌握和改變指定方法的目的。
hook objc_msgSend這種方式的優點是非常精確,而缺點是隻能針對Objective-C方法。對於c方法和block,可以使用libffi 的ffi_call來達成hook。缺點就是編寫維護相關工具門檻高
綜上,如果對於檢查結果精準度要求高的話,推薦使用hool objc_msgSend方式來檢查啟動方法的執行耗時

本文轉載自網路,轉載僅為分享乾貨知識,如有侵權歡迎聯絡雲豹科技進行刪除處理
原文連結:


來自 “ ITPUB部落格 ” ,連結:http://blog.itpub.net/69996194/viewspace-2794059/,如需轉載,請註明出處,否則將追究法律責任。

相關文章