優化Swift的構建時間

2021-08-19 12:24:38 字數 3099 閱讀 4967

原文:regarding swift build time optimizations
上週我拜讀了nickoneill的佳作《加速swift的構建》,之後便不由稍微換了個角度來看待swift的**。

目前有乙個新問題出現:是否該將一行可以算是簡潔的**重構為9行**,以便符合編譯器的需求?對於**來說,簡潔與編譯器友好孰輕孰重?其實,這取決於專案的規模以及開發者的意願。

在舉例之前,我先強調一下手動過濾日誌檔案是非常耗時的。有人設計出了終端命令來簡化這一步驟,不過我的方法更進一步,使用了xcode外掛程式。

雖然初衷只是為了找到並修復最耗時的部分,不過目前我的看法也已經發生了變化:將該過程當成迭代的過程。這樣的做法不僅可以讓**構建效率更高,也能在最開始就防止專案中出現過於耗費時間的函式。

我時常來來回回地檢視不同的git branch,等待乙個專案花費很長時間編譯結束,一直沒想出來為什麼乙個小專案(大約2萬行swift**)要花那麼久時間構建。

在了解到真正的原因後,我必須承認:一行**也需要好幾秒來編譯這件事嚇了我一跳。

我們來看幾個例子!

很顯然,編譯器肯定不喜歡第一種編譯方法,在拆成兩個檢視之後,構建時間減少了99.4%。

// build time: 5238.3ms

return cgsize(width: size.width + (rightview?.bounds

.width ?? 0) + (leftview?.bounds

.width ?? 0) + 22, height: bounds.height)

// build time: 32.4ms

var padding: cgfloat = 22

if let rightview = rightview

if let leftview = leftview

return cgsizemake(size.width + padding, bounds.height)

在**中經常是像下面這樣:

return arrayofstuff + [stuff]

// rather than

return arrayofstuff

我經常會這樣寫**,而這種方式對**的構建時間有很大影響。下面是差距最大的乙個案例,構建時間減少了97.9%。

// build time: 1250.3ms

let systemoptions = [ 7, 14, 30, -1 ]

let systemnames = (0...2).map + [nslocalizedstring("everything", comment: "")]

// some code in-between

labelnames = array(systemnames[0..// build time: 25.5ms

let systemoptions = [ 7, 14, 30, -1 ]

var systemnames = systemoptions.droplast().map

// some code in-between

labelnames = array(systemnames[0..使用if else語句代替了三元運算子,而不進行其它任何改動,構建時間就能縮短92.9%。如果用for迴圈來代替map,構建時間又會縮短75%(不過for迴圈太傷眼了)。

// build time: 239.0ms

let labelnames = type == 0 ? (1...5).map : (0...2).map

// build time: 16.9ms

var labelnames: [string]

iftype == 0

} else

}

這句話有點費解,其實在cgfloat中,有些括號是多餘的,清除掉之後,構建時間會縮短99.9%。

// build time: 3431.7 ms

return

cgfloat(m_pi) * (cgfloat((hour + hourdelta + cgfloat(minute + minutedelta) / 60) * 5) - 15) * unit / 180

// build time: 3.0ms

return

cgfloat(m_pi) * ((hour + hourdelta + (minute + minutedelta) / 60) * 5 - 15) * unit / 180

這個真的很奇怪,下面樣例中的變數混合了本地與例項變數,問題很可能不在rounding本身,而是由於在方法中混用**而導致的,去掉它之後就能大幅縮減所用的時間,準確來講耗費時長減少了97.6%。

// build time: 1433.7ms

let expansion = a — b — c + round(d * 0.66) + e// build time: 34.7ms

let expansion = a — b — c + d * 0.66 + e

注意:所有的對比測量都是在macbook air(13英吋,mid 2013款)上進行的。無論你是否遇到了構建速度緩慢的問題,了解到底是什麼會讓編譯器遇到混亂情況都是很有用的。我肯定你也能發現不少驚喜,作為參考,下面是在我的專案中需要花費5秒多時間構建的完整**。

Swift函式派發優化

與許多其他語言一樣,swift允許類重寫其父類中宣告的方法和屬性。這意味著程式必須在執行時確定要引用哪個方法或屬性,然後執行間接呼叫或間接訪問。這種稱為動態排程的技術以每次間接使用時恆定的執行時開銷為代價提高了語言的表達能力。在對效能敏感的 中,我們不希望花費這些開銷。這篇部落格文章展示了通過消除這...

vue cli構建的專案優化

主要是兩個 1.路由懶載入 這個就是只返回你訪問的資源,其餘的資源不會一下全部載入 2.cdn加速打包 這個玩意的意思就是智慧型尋找離訪問者最近的伺服器站點返回相應資源的意思 路由懶載入 既然是路由懶載入肯定就是跟路由相關了 原本路由是這樣寫的 import vue from vue import ...

swift學習之 函式 構建函式 kvc構建函式

一 函式格式及帶參函式 函式定義格式,函式名 形參列表 返回值 func sum x int,y int int 外部引數,在形參前加乙個名字,外部引數不會影響函式,外部引數讓函式看起來更直觀 外部引數使用 呼叫函式的時候會忽略形參名字 func sum1 number1 x int,number2...