從App啓動開始

App啓動時都幹了哪些事?

通常狀況下,App的啓動分爲冷啓動和熱啓動。git

冷啓動

App點擊啓動前,它的進程不在系統裏,須要系統新建立一個進程給它啓動的狀況,這是一次完成的啓動過程。github

熱啓動

APP在冷啓動後被用戶退到後臺,在App的進程還在系統裏的狀況下,用戶從新啓動進入App的過程,這個過程所作的事情很是少。app

都作了什麼事

通常來講,App的啓動時間,是指用戶點擊App開始,到用戶看到第一個界面以前的時間。包含以下三個階段:異步

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

main()函數執行前

main()函數執行前,系統主要作下面幾件事。函數

  1. 加載可執行文件(App的.o文件的集合)
  2. 加載動態連接庫,進行rebase指針調整和bind符號綁定
  3. Objc運行時的初始處理,包括Objc相關類的註冊、category註冊、selector惟一性檢查等
  4. 初始化,包含了執行+load()方法、attribute((constructor))修飾的函數的調用、建立C++靜態全局變量。

因此通常優化啓動速度的話能夠作以下幾件事:大數據

  1. 減小動態庫加載。每一個庫自己都有依賴關係,蘋果公司建議使用更少的動態庫,而且建議在使用動態庫的數量較多時,儘可能將多個動態庫進行合併。
  2. 減小加載啓動後不會去使用的類和方法。
  3. +load() 方法裏的內容能夠放到首屏渲染完成後再執行,或使用 +initialize() 方法替換掉。由於,在一個 +load() 方法裏,進行運行時方法替換操做會帶來 4 毫秒的消耗。不要小看這 4 毫秒,聚沙成塔,執行 +load() 方法對啓動速度的影響會愈來愈大。
  4. 控制C++全局變量的數量。

main()函數執行後

main()函數執行後的階段,指的是從main()函數執行開始,到appDelegate的didFinishLaunchingWithOptions方法裏首屏渲染相關方法執行完成。優化

首頁的業務代碼都是要在這個階段,主要包括了:線程

  • 首屏初始化所需配置文件的讀寫操做;
  • 首屏列表大數據的讀取;
  • 首屏渲染的大量計算等。

在平常操做中,咱們老是把各類初始化工做都放到這個階段執行,致使渲染完成滯後。指針

更加優化的方法應該是:在功能上梳理出那些是首屏渲染必要的初始化功能,哪些是App啓動必要的初始化功能,哪些是在對應功能開始使用才須要初始化的。將這些初始化功能分別放到合適的階段執行。cdn

首屏渲染完成後

這個階段是從渲染完成時開始,到didFinishLaunchingWithOptions方法做用域結束時結束。

這個階段用戶已經能夠看到App的首頁信息了,因此優化的優先級排在最後。可是那些卡住主線程的方法仍是須要最優先處理的。

怎麼優化

主要是功能級別優化和方法級別優化。

功能級別優化

從main()函數執行後這個階段下手。

優化的思路是:main()函數開始執行到首屏渲染完成前,只處理首屏相關的業務,其餘非首屏業務的初始化、監聽註冊、配置文件的讀寫等都放到首屏渲染完成後去作。

方法級別優化

這個階段主要是檢查首屏渲染完成前,主線程上有哪些耗時方法,將沒必要要的耗時方法滯後或者異步執行。

我的博客 歡迎駐足

相關文章
相關標籤/搜索