2010-11-03 43 views
1

我有一個運行可靠的一個複雜的應用程序,但我很困惑,爲什麼我需要保留一個特定的NSArray(「源」)兩次防止崩潰(儘管沒有異常被報道在控制檯上,但應用程序崩潰並返回到跳板)。需要兩次保留一個NSArray以避免崩潰 - 爲什麼?

代碼的一個片段包含下面。有太多的代碼來粘貼它們,但你有我的話說,沒有明確的調用來釋放數組。 'sources'是一個實例變量。

如果我只保留了陣列一次(或者根本沒有),我得到的崩潰。有兩個保留,該應用程序是完全穩定的。爲什麼我需要保留該數組兩次讚賞

NSString *plistPath = [[NSBundle mainBundle] pathForResource:@"Sources" ofType:@"plist"]; 

sources = [[NSArray arrayWithContentsOfFile:plistPath] autorelease]; 

[sources retain]; 
[sources retain]; 

思考。提前致謝。

回答

7

顯式調用釋放陣列。 autoreleaserelease一樣明確 - 稍後會發生。不僅如此,首先自動釋放數組是錯誤的,因爲您並不擁有它。需要一個retain來聲明該陣列的所有權。第二個通過平衡不正確使用autorelease來防止崩潰。

+0

感謝查克和其他人的回覆,很感激。 – Snips 2010-11-11 01:46:46

3

這與autorelease有關嗎?我看不出爲什麼會出現這種情況:它應該是autoreleases的工廠方法。儘管我不知道添加額外的autorelease會帶來什麼後果,但如果您將其與其中一個保留一起取出,可能值得一看。

+0

自動釋放顯然是不正確的,但是任何人都知道爲什麼它恰恰會導致問題?我會想到,一旦最近的autorelease池知道數組,它會發送一個單一的釋放時,儘管通常autorelease被髮送。顯然不是,但任何人都知道爲什麼? – Cris 2010-11-03 00:29:55

10

您使用+arrayWithContentsOfFile:,它返回一個自動釋放的對象,然後再自動釋放它。拿出電話-autorelease,你會沒事的。您可以重新編寫它:

sources  = [[NSArray arrayWithContentsOfFile:plistPath] retain]; 
+1

這是正確的。欲瞭解更多信息,請參閱內存管理上的這個問題:http://stackoverflow.com/questions/370427/learn-obj-c-memory-management – 2010-11-03 02:21:49

3

對工廠方法溝渠autorelease。這就是爲什麼你需要第二次保留。

2

這是因爲arrayWithContentsOfFile:返回一個autoreleased數組給你。在這個數組上調用autorelease會在當前事件運行循環結束時釋放兩次。

1
NSString *plistPath = [[NSBundle mainBundle] pathForResource:@"Sources" ofType:@"plist"]; 

sources = [[NSArray alloc] initWithContentsOfFile:plistPath];