iOS啟動(dòng)時(shí)間逻澳,頁面的加載時(shí)間優(yōu)化

服務(wù)器斷電了闸天,所以得空來寫點(diǎn)東西,之所以寫這個(gè)問題是因?yàn)橐淮螢觚埵录弊觯晃覀冺?xiàng)目上線引發(fā)了看門狗超時(shí)問題苞氮,就是那個(gè)eatBadfood,然后導(dǎo)致啟動(dòng)時(shí)間超時(shí)瓤逼,高達(dá)27s笼吟,呵呵,啥玩意27s起不來啊抛姑,出問題設(shè)備是iPad但是我們測試時(shí)候沒有遇到。

OK艳狐,那就是我的問題了吧定硝,不多說啟動(dòng)超時(shí)我們就來處理啟動(dòng)超時(shí)的問題。

首先就是需要了解關(guān)于app啟動(dòng)的時(shí)候都干了什么事情毫目,包括我們點(diǎn)擊build按鈕都干了什么:

當(dāng)我們點(diǎn)擊了 build 之后蔬啡,做了什么事情呢?

預(yù)處理(Pre-process):把宏替換镀虐,刪除注釋箱蟆,展開頭文件,產(chǎn)生 .i 文件刮便。

編譯(Compliling):把之前的 .i 文件轉(zhuǎn)換成匯編語言空猜,產(chǎn)生 .s文件。

匯編(Asembly):把匯編語言文件轉(zhuǎn)換為機(jī)器碼文件,產(chǎn)生 .o 文件辈毯。

鏈接(Link):對.o文件中的對于其他的庫的引用的地方進(jìn)行引用坝疼,生成最后的可執(zhí)行文件(同時(shí)也包括多個(gè) .o 文件進(jìn)行 link)。

其實(shí)通常對我們來說的話就是分為編譯階段和執(zhí)行階段谆沃;在我們app代碼里面進(jìn)行區(qū)分就是以main()函數(shù)為間隔區(qū)分這兩個(gè)階段钝凶,main()函數(shù)執(zhí)行之前做的事情就是我們所要進(jìn)行優(yōu)化的地方了,即pre-main:在這段時(shí)間里系統(tǒng)會(huì)進(jìn)行加載動(dòng)態(tài)庫唁影、注冊 Objc 類等系統(tǒng)操作耕陷。

在我們要優(yōu)化之前首先我們要看一下,我們具體看一下啟動(dòng)時(shí)間到底是多少(系統(tǒng)方法):Edit scheme -> Run -> Auguments 將環(huán)境變量 DYLD_PRINT_STATISTICS 設(shè)為 1)然后運(yùn)行据沈,控制臺(tái)就會(huì)打印我們的premain所用的時(shí)間哟沫。

Total pre-main time: 915.59 milliseconds (100.0%)

?? ? ? ? dylib loading time: 499.70 milliseconds (54.5%)

? ? ? ? rebase/binding time:? 48.53 milliseconds (5.3%)

? ? ? ? ? ? ObjC setup time:? 24.47 milliseconds (2.6%)

?? ? ? ? ? initializer time: 342.87 milliseconds (37.4%)

?? ? ? ? ? slowest intializers :

?? ? ? ? ? ? libSystem.B.dylib :? 4.06 milliseconds (0.4%)

? ? libMainThreadChecker.dylib :? 34.28 milliseconds (3.7%)

? ? ? ? ? libglInterpose.dylib : 124.91 milliseconds (13.6%)

? ? ? ? ? ? ? ? ? ? ? ? Pretty : 263.99 milliseconds (28.8%)

? total time: 1.8 seconds (100.0%)

? total images loaded:? 573 (523 from dyld shared cache)

? total segments mapped: 195, into 13129 pages

? total images loading time: 1.2 seconds (66.3%)

? total load time in ObjC:? 24.47 milliseconds (1.2%)

? total debugger pause time: 759.18 milliseconds (40.0%)

? total dtrace DOF registration time:? 0.00 milliseconds (0.0%)

? total rebase fixups:? 279,519

? total rebase fixups time:? 40.52 milliseconds (2.1%)

? total binding fixups: 720,435

? total binding fixups time: 222.74 milliseconds (11.7%)

? total weak binding fixups time:? 8.30 milliseconds (0.4%)

? total redo shared cached bindings time: 223.03 milliseconds (11.7%)

? total bindings lazily fixed up: 0 of 0

? total time in initializers and ObjC +load: 342.87 milliseconds (18.0%)

?? ? ? ? ? ? ? ? ? ? ? ? libSystem.B.dylib :? 4.06 milliseconds (0.2%)

?? ? ? ? ? ? ? libBacktraceRecording.dylib :? 5.84 milliseconds (0.3%)

? ? ? ? ? ? ? ? libMainThreadChecker.dylib :? 34.28 milliseconds (1.8%)

? ? ? ? ? ? ? ? ? ? ? libglInterpose.dylib : 124.91 milliseconds (6.5%)

? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? CoreDuet :? 2.50 milliseconds (0.1%)

?? ? ? ? ? ? ? ? ? ? ? libMTLCapture.dylib :? 2.71 milliseconds (0.1%)

? ? ? ? ? ? ? libViewDebuggerSupport.dylib :? 8.01 milliseconds (0.4%)

? ? ? ? ? ? ? ? ? ? ? ? ? ? ? FBSDKCoreKit :? 4.42 milliseconds (0.2%)

? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? Pretty : 263.99 milliseconds (13.9%)

total symbol trie searches:? ? 1703506

total symbol table binary searches:? ? 0

total images defining weak symbols:? 59

total images using weak symbols:? 136

其實(shí)看起來還是很亂七八糟的,因?yàn)槲以趀nvironment里添加了另外一行:DYLD_PRINT_STATISTICS_DETAILS為YES卓舵,然后打印的就如上這么詳細(xì)了南用。

反正我當(dāng)時(shí)看的時(shí)候是一臉懵逼,這都是啥掏湾,多虧了有大神指點(diǎn)裹虫,我們可以來詳細(xì)的分析:

pre-main時(shí)間主要由 4 部分組成(原文搬運(yùn)):

1.dylib loading:

這一階段 dyld 會(huì)分析應(yīng)用依賴的 dylib ,所以融击,依賴的 dylib 越少越好筑公。在這一步,我們能做的優(yōu)化就是檢查是否存在不需要的 dylib 尊浪,移除不必要的 dylib 匣屡。

在項(xiàng)目優(yōu)化實(shí)踐中,我們移除了一個(gè)沒有必要的動(dòng)態(tài)庫拇涤,并將幾個(gè)動(dòng)態(tài)庫合成為一個(gè)動(dòng)態(tài)庫捣作,減少動(dòng)態(tài)庫數(shù)量。

2.rebase/binding:

這一階段系統(tǒng)主要注冊 Objc 類鹅士。所以券躁,指針數(shù)量越少越好。這一步能做的優(yōu)化有:

清理項(xiàng)目中無用的類

刪減沒有被調(diào)用到或者已經(jīng)廢棄的方法

刪減一些無用的靜態(tài)變量

可通過 AppCode 等工具掃描項(xiàng)目中未使用的代碼掉盅。

3.Objc srtup:

這一階段沒有什么特別能優(yōu)化的地方也拜,如果 rebase/binding 階段優(yōu)化的好這步耗時(shí)也會(huì)很少。

4.initializer:

這一階段趾痘,dyld 開始運(yùn)行程序的初始化函數(shù)慢哈,調(diào)用每個(gè) Objc 類和分類的 +load 方法,調(diào)用 C/C++ 中的構(gòu)造器函數(shù)永票。initializer階段執(zhí)行完后卵贱,dyld 開始調(diào)用 main() 函數(shù)滥沫。在這一步,檢查 +load 方法艰赞,盡量把事情推遲到 +initiailize 方法里執(zhí)行佣谐。

在這里我們修改了部分原本代碼中直接在 +load 函數(shù)初始化邏輯改為在 +initialize 中加載,也就是到使用時(shí)才加載方妖。

參考以上的教程狭魂,我尋找了我們app的需要優(yōu)化的地方,拼命減少了一個(gè)動(dòng)態(tài)庫党觅,還有幾個(gè)三方庫雌澄,把一些用來測試的指針都給干掉了,當(dāng)然因?yàn)槭切碌腶pp杯瞻,所以沒有用app code檢測镐牺,以后可以使用試試。

雖然我沒看出來啟動(dòng)時(shí)間有啥進(jìn)步魁莉,但是改了就是進(jìn)步了安墙А;美滋滋提交旗唁,求神拜佛畦浓,結(jié)果同樣問題,同樣結(jié)果检疫。

我就開始總結(jié)讶请,這個(gè)問題一開始就和啟動(dòng)時(shí)間沒有關(guān)系啊,再超時(shí)也不可能27s嘛屎媳,第二次打回來告訴我32s夺溢,這就更離譜了,所以我進(jìn)行了錯(cuò)誤日志解析烛谊,呵呵风响,原來是三方庫的問題(百度地圖sdk導(dǎo)致);所以建議在finishLaunch的時(shí)候部分三方注冊丹禀,代理的內(nèi)容可以放到子線程做状勤。

我們回過頭來看啟動(dòng)時(shí)間的問題,我們通過上面對照能夠看懂我們程序所打印的內(nèi)容湃崩,如果能夠獲取程序在各個(gè)頁面顯示出來所占用的時(shí)間荧降,然后我們才能進(jìn)行具體優(yōu)化接箫,判斷是否有我們?nèi)庋鬯床坏降目D問題攒读。

下面是正文:

1.premain()以后的顯示的頁面時(shí)間優(yōu)化

? ? (1).在我們首頁顯示之前,盡量減少操作辛友。

? ? 例如:各種網(wǎng)絡(luò)請求薄扁,能省就省了吧剪返;能用代碼構(gòu)建UI,盡量少用xib邓梅;手勢等添加可以在頁面顯示之后脱盲;減少加載的view controller的加載數(shù)量;部分可以延時(shí)處理的操作可以放到子線程日缨。

? ? 至于使用動(dòng)畫钱反,個(gè)人覺得就算了吧,如果不是特別熟練清楚底層原理匣距,建議不要使用(動(dòng)畫不會(huì)被主線程阻塞)

? ? (2).頁面卡頓的優(yōu)化

? ? 這里感覺能優(yōu)化的就有很多了面哥,可以通過bugly來監(jiān)測一些卡頓問題,通過具體代碼去解決問題毅待。

? ? 還有關(guān)于CPU和GPU尚卫,頁面渲染相關(guān)的問題我也正在學(xué)習(xí)階段,建議大家多讀大神文章尸红,一起學(xué)習(xí)吧吱涉。畢竟我也是菜的不行。

2.頁面加載耗時(shí)打印

? ? 打印各個(gè)頁面加載時(shí)間,有助于我們發(fā)現(xiàn)很多平時(shí)看不到的問題蚤假,對比得到哪些頁面需要去優(yōu)化悯森。

? ? 下面我來介紹一下具體方法:

? ? 我們想要了解加載頁面的view消耗的時(shí)間需要知道VC的生命周期:

? ??1.initWithCoder: 通過 nib 文件初始化時(shí)觸發(fā)。

????2.awakeFromNib: nib 文件被加載的時(shí)候疙咸,會(huì)發(fā)生一個(gè) awakeFromNib 的消息到 nib 文件中的每個(gè)對象。

????3.loadView: 開始加載視圖控制器自帶的 view风科。

????4.viewDidLoad: 視圖控制器的 view 被加載完成撒轮。

????5.viewWillAppear: 視圖控制器的 view 將要顯示在 window 上。

????6.updateViewConstraints: 視圖控制器的 view 開始更新 AutoLayout 約束贼穆。????????????

????7.viewWillLayoutSubviews:視圖控制器的 view 將要更新內(nèi)容視圖的位置题山。

????8.viewDidLayoutSubviews: 視圖控制器的 view 已經(jīng)更新視圖的位置。

????9.viewDidAppear: 視圖控制器的 view 已經(jīng)展示到 window 上故痊。

????10.viewWillDisappear: 視圖控制器的 view 將要從 window 上消失顶瞳。

????11.viewDidDisappear: 視圖控制器的 view 已經(jīng)從 window 上消失。

? ? 所以愕秫,我們只需要在loadview的時(shí)候打印一下當(dāng)前時(shí)間[[NSDate date] timeIntervalSince1970]慨菱,因?yàn)楂@取到的時(shí)間單位是秒,建議*1000換算成毫秒戴甩,看起來比較直觀符喝。在viewDidAppear里面再打印一次當(dāng)前時(shí)間,兩個(gè)時(shí)間的差值就是頁面的加載時(shí)間啦甜孤,如果加載時(shí)間太久协饲,那就需要進(jìn)行優(yōu)化了畏腕。(也得根據(jù)自己的代碼具體細(xì)節(jié)進(jìn)行調(diào)整,建議在loadview進(jìn)行UI布局)

剛剛打印了一下時(shí)間:當(dāng)前開始加載1577944446238

當(dāng)前結(jié)束加載1577944446251

這不是扯么茉稠,速度這么快描馅?我都不信,但是這是事實(shí)而线,這是沒有進(jìn)行網(wǎng)絡(luò)加載的铭污,單純的加載UI的時(shí)間,不包括刷新方法膀篮;你需要在你需要的地方進(jìn)行布局埋點(diǎn)况凉,統(tǒng)計(jì)這個(gè)頁面的加載時(shí)間。

有更好的方法的小伙伴各拷,歡迎留言刁绒。

參考:http://www.reibang.com/p/6387eba2ea16

https://www.cnblogs.com/junhuawang/p/7598236.html

http://www.reibang.com/p/fe566ec32d28

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末,一起剝皮案震驚了整個(gè)濱河市烤黍,隨后出現(xiàn)的幾起案子知市,更是在濱河造成了極大的恐慌,老刑警劉巖速蕊,帶你破解...
    沈念sama閱讀 219,270評論 6 508
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件嫂丙,死亡現(xiàn)場離奇詭異,居然都是意外死亡规哲,警方通過查閱死者的電腦和手機(jī)跟啤,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 93,489評論 3 395
  • 文/潘曉璐 我一進(jìn)店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來唉锌,“玉大人隅肥,你說我怎么就攤上這事“兰颍” “怎么了腥放?”我有些...
    開封第一講書人閱讀 165,630評論 0 356
  • 文/不壞的土叔 我叫張陵,是天一觀的道長绿语。 經(jīng)常有香客問我秃症,道長,這世上最難降的妖魔是什么吕粹? 我笑而不...
    開封第一講書人閱讀 58,906評論 1 295
  • 正文 為了忘掉前任种柑,我火速辦了婚禮,結(jié)果婚禮上匹耕,老公的妹妹穿的比我還像新娘聚请。我一直安慰自己,他們只是感情好泌神,可當(dāng)我...
    茶點(diǎn)故事閱讀 67,928評論 6 392
  • 文/花漫 我一把揭開白布良漱。 她就那樣靜靜地躺著,像睡著了一般欢际。 火紅的嫁衣襯著肌膚如雪母市。 梳的紋絲不亂的頭發(fā)上,一...
    開封第一講書人閱讀 51,718評論 1 305
  • 那天损趋,我揣著相機(jī)與錄音患久,去河邊找鬼。 笑死浑槽,一個(gè)胖子當(dāng)著我的面吹牛蒋失,可吹牛的內(nèi)容都是我干的。 我是一名探鬼主播桐玻,決...
    沈念sama閱讀 40,442評論 3 420
  • 文/蒼蘭香墨 我猛地睜開眼篙挽,長吁一口氣:“原來是場噩夢啊……” “哼!你這毒婦竟也來了镊靴?” 一聲冷哼從身側(cè)響起铣卡,我...
    開封第一講書人閱讀 39,345評論 0 276
  • 序言:老撾萬榮一對情侶失蹤,失蹤者是張志新(化名)和其女友劉穎偏竟,沒想到半個(gè)月后煮落,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體,經(jīng)...
    沈念sama閱讀 45,802評論 1 317
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡踊谋,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 37,984評論 3 337
  • 正文 我和宋清朗相戀三年蝉仇,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片殖蚕。...
    茶點(diǎn)故事閱讀 40,117評論 1 351
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡轿衔,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出睦疫,到底是詐尸還是另有隱情呀枢,我是刑警寧澤,帶...
    沈念sama閱讀 35,810評論 5 346
  • 正文 年R本政府宣布笼痛,位于F島的核電站裙秋,受9級特大地震影響,放射性物質(zhì)發(fā)生泄漏缨伊。R本人自食惡果不足惜摘刑,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,462評論 3 331
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望刻坊。 院中可真熱鬧枷恕,春花似錦、人聲如沸谭胚。這莊子的主人今日做“春日...
    開封第一講書人閱讀 32,011評論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽。三九已至胡控,卻和暖如春扳剿,著一層夾襖步出監(jiān)牢的瞬間,已是汗流浹背昼激。 一陣腳步聲響...
    開封第一講書人閱讀 33,139評論 1 272
  • 我被黑心中介騙來泰國打工庇绽, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留,地道東北人橙困。 一個(gè)月前我還...
    沈念sama閱讀 48,377評論 3 373
  • 正文 我出身青樓瞧掺,卻偏偏與公主長得像,于是被迫代替她去往敵國和親凡傅。 傳聞我的和親對象是個(gè)殘疾皇子辟狈,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 45,060評論 2 355