我的 iOS 記憶體偵錯之旅:初探 Instruments Allocations 專案中的「壞味道」引發了我的好奇心

更新於 發佈於 閱讀時間約 7 分鐘
最近新接手了一個舊的 iOS 專案,在熟悉程式碼的過程中,我發現了一些普遍存在的「壞味道 (Code Smell)」:delegate 普遍沒有使用 weak,而畫面的切換大量依賴 present,卻很少看到對應的 dismiss。
一個矛盾的現象是:這個專案已上架,但似乎沒有什麼毀滅性的閃退回報。這引發了我的思考,這些理論上的「架構缺陷」在實際運行中到底造成了多大的影響?
為了搞清楚這個問題,我決定去探索一個我此前並不熟悉的工具——Instruments,並使用其中的 Allocations 來記錄下這段探索之旅。

建立「實驗室」:用 Edge Case 測試來放大問題

直接在複雜的正式專案裡分析,對我這個 Instruments 工具新手來說太困難了。所以我做的第一件事,就是建立一個獨立、乾淨的測試專案。我的想法很簡單:如果我想看清楚問題,就必須先把它放大

這個專案的目標很純粹:模擬並放大那兩種「壞味道」的影響。我設計了幾個按鈕,用來進行極端測試(Edge Case Test):

  1. 一次性在記憶體中創建大量「會洩漏的」 ViewController 實例。
  2. 一次性釋放它們。
  3. 用同樣的方式,創建和釋放「正常的」 ViewController 作為對照組。

初探 Allocations:看懂曲線背後的意義

在 Xcode 中,我透過 Product > Profile 啟動了 Instruments,選擇 Allocations,然後點擊紅色的錄製按鈕,我的測試正式開始。

以下是我在創建了上萬個物件後,進行釋放操作的對照圖:

raw-image

上圖一:當我點擊「釋放 LeakyVC」後,記憶體曲線並沒有如預期般下降,Persistent 值依然很高。


raw-image

圖二:我點擊「釋放 CorrectVC」後,記憶體曲線如預期般下降,Persistent 值也降了下來。

眼前的畫面讓我非常興奮!雖然我對 Persistent、Transient 這些術語還是一知半解,但這條沒有降下去的藍色曲線,就是最直觀的證據。它告訴我,有些東西被留下來了。

經過查詢,這兩個關鍵詞的意義:

  • Persistent (持續存在):這是在我停止記錄時,依然存活在記憶體中的物件。它就是我洩漏的「贓物」。
  • Transient (短暫存在):這是在記錄過程中,被創建出來、但又被成功釋放掉了的物件。

這個強烈的視覺對比,讓我第一次如此直觀地「看見」了記憶體洩漏。

從數據到根源:解讀 Allocations 列表

有了測試專案的經驗,我回頭分析正式專案的 Allocations 報告,這一次我不再迷茫。我知道要關注 Persistent 這一欄,並從中尋找元兇。

raw-image

有兩行數據立刻吸引了我的注意:

  1. VM: Allocation 512.00 MiB:一個佔用了整整 512MB 虛擬記憶體的單一區塊。我了解到這通常和 WKWebView 為了效能而預留的空間有關。
  2. VM: UILabel (CALayer):這一項佔用了 136.84 MiB!並且我注意到,每次操作後它的 Persistent 值都會累加,但 Transient 欄位卻沒有對應增加。這強烈暗示著有大量的 View 沒有被釋放。

這兩條線索,與我最初在程式碼中看到的兩種「壞味道」完美地對應了起來:

  • 那個洩漏的 512MB VM 區塊,很可能就是一個 WKWebView 因為 delegate 強引用循環而無法被釋放的結果。
  • 而那龐大的 136MB UILabel 記憶體,則無疑是 ViewController 不斷 present 堆疊,導致巨量 View 被累積在記憶體中的直接後果。

藉助 Call Tree 功能(並進行如下圖的設定),我很快就定位到了那個被遺忘 weak 的 delegate,證實了我的猜想。

raw-image

偵錯之外的兩個重要發現

這次的偵錯之旅,除了最終定位到問題根源,更有趣的是我在測試過程中得到的兩個重要發現。它們顛覆了我之前的一些刻板印象。

發現一:deinit 是最誠實的「生命指標」

deinit {
print("deinit -- 我被成功釋放了!")
}

我學到的第一個技巧,就是在 deinit 裡加上 print 語句。這個簡單的動作,成爲了我判斷物件生命週期是否正常的可靠指標。當記憶體洩漏發生時,無論我怎麼操作,控制台都是一片死寂;而修復問題後,每一次物件被釋放,控制台都會準確地打印出 deinit 的訊息。這給人一種安心的確定感,就像是親眼看到物件在揮手告別。

發現二:健康的釋放是有「成本」的,一次短暫的卡頓勝過虛假的流暢

在我的 Edge Case 測試中,一個現象讓我印象極其深刻:當我一次性釋放 10000 個正常物件時,App 的 UI 會出現一次短暫的、可感知的卡頓,隨後記憶體才成功下降。與此形成鮮明對比的是,在洩漏的版本中,「釋放」操作卻異常順暢

這讓我恍然大悟:釋放記憶體是需要 CPU 在主執行緒上工作的。那一次短暫的卡頓,正是系統在努力呼叫上萬次 deinit、進行記憶體大掃除的證明。而那個「順暢」的假象,恰恰是因為 App 什麼都沒做,只是把清理工作跳過了,將問題永遠地留在了記憶體裡。

從此以後,我知道了不能只追求表面的流,更要理解背後發生的事。

結語:從陌生到熟悉的喜悅

這次的偵錯之旅,從我對一個舊專案「架構缺陷」的好奇心開始,最終以我對 iOS 記憶體管理更深的理解結束。

我明白了,那些看似沒有引發立即閃退的問題,並非無關緊要。它們會像溫水煮青蛙一樣,持續蠶食 App 的效能和穩定性,直到某一天在某個用戶的低階設備上,爆發為一次致命的閃退。

這次經歷讓我體會到,面對未知工具時,主動學習、動手實踐的過程本身,就是最有價值的收穫。現在,Instruments 的 Allocations 工具對我來說,不再是個令人望而生畏的面板,而是一個可以信賴的夥伴,幫助我深入洞察 App 的內部運作,寫出更健壯、更高效的程式碼。

留言
avatar-img
留言分享你的想法!
avatar-img
Xian wu的沙龍
0會員
2內容數
你可能也想看
Thumbnail
透過蝦皮分潤計畫,輕鬆賺取零用金!本文分享5-6月實測心得,包含數據流程、實際收入、平臺優點及注意事項,並推薦高分潤商品,教你如何運用空閒時間創造被動收入。
Thumbnail
透過蝦皮分潤計畫,輕鬆賺取零用金!本文分享5-6月實測心得,包含數據流程、實際收入、平臺優點及注意事項,並推薦高分潤商品,教你如何運用空閒時間創造被動收入。
Thumbnail
單身的人有些會養寵物,而我養植物。畢竟寵物離世會傷心,植物沒養好再接再厲就好了~(笑)
Thumbnail
單身的人有些會養寵物,而我養植物。畢竟寵物離世會傷心,植物沒養好再接再厲就好了~(笑)
Thumbnail
不知你有沒有過這種經驗?衛生紙只剩最後一包、洗衣精倒不出來,或電池突然沒電。這次一次補貨,從電池、衛生紙到洗衣精,還順便分享使用心得。更棒的是,搭配蝦皮分潤計畫,愛用品不僅自己用得安心,分享給朋友還能賺回饋。立即使用推薦碼 X5Q344E,輕鬆上手,隨時隨地賺取分潤!
Thumbnail
不知你有沒有過這種經驗?衛生紙只剩最後一包、洗衣精倒不出來,或電池突然沒電。這次一次補貨,從電池、衛生紙到洗衣精,還順便分享使用心得。更棒的是,搭配蝦皮分潤計畫,愛用品不僅自己用得安心,分享給朋友還能賺回饋。立即使用推薦碼 X5Q344E,輕鬆上手,隨時隨地賺取分潤!
Thumbnail
身為一個典型的社畜,上班時間被會議、進度、KPI 塞得滿滿,下班後只想要找一個能夠安靜喘口氣的小角落。對我來說,畫畫就是那個屬於自己的小樹洞。無論是胡亂塗鴉,還是慢慢描繪喜歡的插畫人物,那個專注在筆觸和色彩的過程,就像在幫心靈按摩一樣,讓緊繃的神經慢慢鬆開。
Thumbnail
身為一個典型的社畜,上班時間被會議、進度、KPI 塞得滿滿,下班後只想要找一個能夠安靜喘口氣的小角落。對我來說,畫畫就是那個屬於自己的小樹洞。無論是胡亂塗鴉,還是慢慢描繪喜歡的插畫人物,那個專注在筆觸和色彩的過程,就像在幫心靈按摩一樣,讓緊繃的神經慢慢鬆開。
Thumbnail
我們經常使用 iPhone 工作、溝通,因此裝置會存有大量的對話紀錄與重要數據。 遇到 Apple 手機遺失的問題時,你一定會擔心資料外洩的風險,但究竟要從何下手找回手機呢? 蘋果向來非常注重用戶的個資安全,所以開發了「尋找」程式與 iPhone 遺失模式, 以協助你找回不見的裝置。不管是
Thumbnail
我們經常使用 iPhone 工作、溝通,因此裝置會存有大量的對話紀錄與重要數據。 遇到 Apple 手機遺失的問題時,你一定會擔心資料外洩的風險,但究竟要從何下手找回手機呢? 蘋果向來非常注重用戶的個資安全,所以開發了「尋找」程式與 iPhone 遺失模式, 以協助你找回不見的裝置。不管是
Thumbnail
很多 Apple 用戶都很喜歡透過內建備忘錄App來筆記, 要是不小心在 iOS 或 iPadOS 備忘錄內紀錄不見、寫錯字或打錯字,要怎麼替 iPad 或 iPhone 備忘錄還原上一步呢? 要是不小心在備忘錄內消失紀錄, 可以利用本篇分享的四招 iPad iPhone備忘錄還原上一步技
Thumbnail
很多 Apple 用戶都很喜歡透過內建備忘錄App來筆記, 要是不小心在 iOS 或 iPadOS 備忘錄內紀錄不見、寫錯字或打錯字,要怎麼替 iPad 或 iPhone 備忘錄還原上一步呢? 要是不小心在備忘錄內消失紀錄, 可以利用本篇分享的四招 iPad iPhone備忘錄還原上一步技
Thumbnail
在行動裝置安全日益嚴峻的環境下,保護手機資料至關重要。使用者除了養成良好的使用習慣之外,也需要定期更新手機OS系統來提升資料安全防護力,而企業端也可以透過APP加殼加密的方式,讓APP達到更高水平的防護。
Thumbnail
在行動裝置安全日益嚴峻的環境下,保護手機資料至關重要。使用者除了養成良好的使用習慣之外,也需要定期更新手機OS系統來提升資料安全防護力,而企業端也可以透過APP加殼加密的方式,讓APP達到更高水平的防護。
Thumbnail
我們經常使用 iPhone 工作、溝通,因此裝置會存有大量的對話紀錄與重要數據。 遇到 Apple 手機遺失的問題時,你一定會擔心資料外洩的風險,但究竟要從何下手找回手機呢? 蘋果向來非常注重用戶的個資安全,所以開發了「尋找」程式與 iPhone 遺失模式, 以協助你找回不見的裝置。不管是手機
Thumbnail
我們經常使用 iPhone 工作、溝通,因此裝置會存有大量的對話紀錄與重要數據。 遇到 Apple 手機遺失的問題時,你一定會擔心資料外洩的風險,但究竟要從何下手找回手機呢? 蘋果向來非常注重用戶的個資安全,所以開發了「尋找」程式與 iPhone 遺失模式, 以協助你找回不見的裝置。不管是手機
Thumbnail
很多 Apple 用戶都很喜歡透過內建備忘錄App來筆記, 要是不小心在 iOS 或 iPadOS 備忘錄內紀錄不見、寫錯字或打錯字,要怎麼替 iPad 或 iPhone 備忘錄還原上一步呢? 要是不小心在備忘錄內消失紀錄, 可以利用本篇分享的四招 iPad iPhone備忘錄還原上一步技
Thumbnail
很多 Apple 用戶都很喜歡透過內建備忘錄App來筆記, 要是不小心在 iOS 或 iPadOS 備忘錄內紀錄不見、寫錯字或打錯字,要怎麼替 iPad 或 iPhone 備忘錄還原上一步呢? 要是不小心在備忘錄內消失紀錄, 可以利用本篇分享的四招 iPad iPhone備忘錄還原上一步技
Thumbnail
一般用戶不建議升級至 iOS 18 測試版,因為這個版本可能存在大量Bug和不穩定因素,導致如 LINE 功能錯誤或銀行 App 閃退等問題。Apple 釋出的 iOS 18 Beta 測試版本主要供開發者使用,並非穩定的正式版。建議等待正式版於9月推出後再考慮更新。
Thumbnail
一般用戶不建議升級至 iOS 18 測試版,因為這個版本可能存在大量Bug和不穩定因素,導致如 LINE 功能錯誤或銀行 App 閃退等問題。Apple 釋出的 iOS 18 Beta 測試版本主要供開發者使用,並非穩定的正式版。建議等待正式版於9月推出後再考慮更新。
Thumbnail
iPhone 因其美觀外形、品質與使用體驗而受到廣大使用者喜愛, 全球的蘋果迷數量龐大。每年 iOS 推出新版本後, 許多用戶都熱切期待體驗新功能,蘋果在滿足用戶需求方面做得相當出色。 然而,有些小問題如 iPhone 發燙、訊號差等, 也讓使用者感到困擾。今天我們要討論的是 iPhon
Thumbnail
iPhone 因其美觀外形、品質與使用體驗而受到廣大使用者喜愛, 全球的蘋果迷數量龐大。每年 iOS 推出新版本後, 許多用戶都熱切期待體驗新功能,蘋果在滿足用戶需求方面做得相當出色。 然而,有些小問題如 iPhone 發燙、訊號差等, 也讓使用者感到困擾。今天我們要討論的是 iPhon
Thumbnail
要不要將 iPhone 更新到 iOS 17.4 版本,通常會這問題大多是擔心設備升級後會引起不少問題, 或是擔心 iOS 17.4 災情會造成耗電或異常錯誤,要是你有這些疑慮, 倒是可以透過這篇 iOS 17.4 災情回報專區了解, 能夠知道大多數 iPhone 用戶在升級後體驗感受和可能會
Thumbnail
要不要將 iPhone 更新到 iOS 17.4 版本,通常會這問題大多是擔心設備升級後會引起不少問題, 或是擔心 iOS 17.4 災情會造成耗電或異常錯誤,要是你有這些疑慮, 倒是可以透過這篇 iOS 17.4 災情回報專區了解, 能夠知道大多數 iPhone 用戶在升級後體驗感受和可能會
追蹤感興趣的內容從 Google News 追蹤更多 vocus 的最新精選內容追蹤 Google News