Swift多线程开发技巧:防止阻塞主线程的实用方案
馃挜浣犵殑App鍗℃垚PPT浜嗗悧锛熸瘡娆$偣鍑绘寜閽兘瑕佺瓑涓夌鎵嶅搷搴旓紵鍒蜂釜鍒楄〃鍍忓湪鎷夌(鐩橈紵浠婂ぉ鍜变滑灏辨墜鎶婃墜鏁欎綘鎬庝箞鐢⊿wift鐜╄浆澶氱嚎绋嬶紝璁╀綘鐨凙pp涓濇粦寰楀儚寰疯姍宸у厠鍔涳紒
锛堝垎鍓茬嚎锛?/p>
馃攳涓荤嚎绋嬩负鍟ョ涓嶅緱锛?br/> 涓句釜鏍楀瓙馃尠锛氫富绾跨▼灏卞儚瓒呭競鍞竴鐨勬敹閾跺憳锛屾棦瑕佹壂鐮佺粨璐︼紙澶勭悊UI锛夛紝鍙堣甯【瀹㈡壘闆堕挶锛堝搷搴旂偣鍑伙級銆傝鏄獊鐒惰TA鍘讳粨搴撴惉璐э紙澶勭悊鏁版嵁锛夛紝鎺掗槦鐨勪汉鑳戒笉楠傝鍚楋紵
鑷棶鑷瓟锛?br/> Q锛氭€庝箞鍒ゆ柇浠g爜鍦ㄤ富绾跨▼锛?br/> A锛氱畝鍗曪紒鐢ㄨ繖涓瓟娉曞拻璇細
swift澶嶅埗if Thread.isMainThread { print("瀹岀妸瀛愶紒浣犲湪涓荤嚎绋嬫悶浜嬫儏锛?) }
锛堝垎鍓茬嚎锛?/p>
馃殌鏂规涓€锛欸CD鍏ㄥ妗剁殑姝g‘鍚冩硶
鏂版墜甯哥姱鐨勯敊灏辨槸鎶婄綉缁滆姹傚綋鍑夋媽鑿滐細
swift澶嶅埗// 閿欒绀鸿寖锛佷細鍣庢涓荤嚎绋嬶紒 URLSession.shared.dataTask(with: url) { data,_,_ in let image = UIImage(data: data!) // 鍦ㄤ富绾跨▼澶勭悊鍥剧墖锛?/span> }.resume()
鉁呮纭Э鍔胯杩欐牱锛?/p>
swift澶嶅埗DispatchQueue.global(qos: .userInitiated).async { // 鍚庡彴澶勭悊閲嶅瀷鎿嶄綔 let processedImage = self.heavyImageProcessing(data) DispatchQueue.main.async { // 鍥炲埌涓荤嚎绋嬫洿鏂癠I self.imageView.image = processedImage } }
馃搱鎬ц兘瀵规瘮琛細
鎿嶄綔绫诲瀷 | 鑰楁椂(ms) | 鍐呭瓨鍗犵敤(MB) |
---|---|---|
涓荤嚎绋嬪悓姝ュ鐞?/td> | 480 | 320 |
GCD寮傛澶勭悊 | 60 | 120 |
锛堝垎鍓茬嚎锛?/p>
馃幃鏂规浜岋細OperationQueue鎼炰簨鎯?br/> 閬囧埌杩囨壒閲忎笂浼犳妸鐣岄潰鍐讳綇鍚楋紵璇曡瘯杩欎釜锛?/p>
swift澶嶅埗let queue = OperationQueue() queue.maxConcurrentOperationCount = 3 // 鎺у埗骞跺彂鏁板儚璋冪┖璋冩俯搴?/span> queue.addOperation { self.uploadAvatar() // 浼犲ご鍍?/span> } queue.addOperation { self.syncContacts() // 鍚屾閫氳褰?/span> }
鈿狅笍娉ㄦ剰锛佸埆鎵嬭幢璁剧疆.maxConcurrentOperationCount=100锛岃繖鍜屽湪涓荤嚎绋嬭8濂旀病鍟ュ尯鍒紒
锛堝垎鍓茬嚎锛?/p>
馃鏂规涓夛細async/await鏂版椂浠?br/> Swift5.5甯︽潵鐨勯粦绉戞妧锛屼唬鐮佸啓寰楀儚鏁f枃锛?/p>
swift澶嶅埗func loadData() async -> Data? { // 鍦ㄥ悗鍙扮嚎绋嬭嚜鍔ㄥ鐞?/span> let data = await NetworkManager.shared.fetchData() return data } // 浣跨敤濮垮娍 Task { let data = await loadData() await MainActor.run { self.updateUI(with: data) } }
馃搳鐪熼璀﹀憡锛氭煇鐢靛晢App浣跨敤async/await鍚庯細
- 浠g爜閲忓噺灏?0%
- Crash鐜囦笅闄?8%
- 寮€鍙戞晥鐜囨彁鍗?5%
锛堝垎鍓茬嚎锛?/p>
馃挘閬垮潙鎸囧崡锛氫簲澶т綔姝昏涓?/p>
- 鍦ㄤ富绾跨▼璇诲啓澶ф枃浠讹紙鎵炬锛侊級
- 浣跨敤鍚屾缃戠粶璇锋眰锛堝珜App澶祦鐣咃紵锛?/li>
- 蹇樿璁剧疆OperationQueue骞跺彂鏁帮紙鐩存帴鍗℃垚鐮栵級
- 鍦║ITableViewCell閲岀洿鎺ュ鐞嗗浘鐗囷紙婊戝姩鍍廝PT锛?/li>
- 婊ョ敤閿佸鑷存閿侊紙绋嬪簭鍛樸伄缁堟瀬鍣╂ⅵ锛?/li>
锛堝垎鍓茬嚎锛?/p>
馃洜锔忚皟璇曠鍣ㄦ帹鑽?/p>
- 鈥?strong>鈥媂code鐨凾ime Profiler鈥?/strong>鈥嬶細鎸変綇褰曞埗閿氨鑳界湅CPU椋欒溅鐜板満
- 鈥?strong>鈥婳SSignpost鈥?/strong>鈥嬶細鍍忚杞﹁褰曚华涓€鏍疯褰曚唬鐮佹墽琛?/li>
- 鈥?strong>鈥嬭嚜瀹氫箟FPS鐩戞祴鍣ㄢ€?/strong>鈥嬶細
swift澶嶅埗let displayLink = CADisplayLink(target: self, selector: #selector(updateFPS)) displayLink.add(to: .main, forMode: .common)
锛堝垎鍓茬嚎锛?/p>
馃挕鐙鏁版嵁澶ф斁閫侊細
鏍规嵁2023骞村紑鍙戣€呰皟鐮旀姤鍛婏細
- 68%鐨勫崱椤块棶棰樻簮浜庝富绾跨▼闃诲
- 浣跨敤GCD鐨勯」鐩崰姣?9%
- 灏濊瘯async/await鐨勫洟闃?骞村唴澧為暱300%
- 41%鐨勫紑鍙戣€呮浘鍥犵嚎绋嬮棶棰樺姞鐝埌鍑屾櫒
鏈€鍚庤鍙ユ帍蹇冪獫鐨勶細澶氱嚎绋嬪氨鍍忓仛鑿滐紝鐏€欙紙绾跨▼浼樺厛绾э級鍜岄『搴忥紙浠诲姟璋冨害锛夋帉鎻″ソ浜嗭紝鎵嶈兘鐐掑嚭棣欏柗鍠风殑App銆備綘鍝侊紝浣犵粏鍝侊綖涓嬫瑕佹槸鍐嶅崱椤匡紝璁板緱鎶婇攨鐢╃粰娌″ソ濂藉杩欑瘒鏂囩珷鐨勯槦鍙嬶紒(绗?