2010-03-28 45 views
4

我目前正在處理的代碼需要添加一個NSNumber對象到一個數組。所有的值爲0-12的NSNumbers都添加好了,但是13以後會導致EXC_BAD_ACCESS。我打開NSZombieEnabled,現在變得*** -[CFNumber retain]: message sent to deallocated instance 0x3c78420NSNumber> = 13不會保留。一切都會

這裏的調用堆棧:
#0 0x01eac3a7 in ___forwarding___
#1 0x01e886c2 in __forwarding_prep_0___
#2 0x01e3f988 in CFRetain
#3 0x01e4b586 in _CFArrayReplaceValues
#4 0x0002a2f9 in -[NSCFArray insertObject:atIndex:]
#5 0x0002a274 in -[NSCFArray addObject:]
#6 0x00010a3b in -[Faves addObject:] at Faves.m:24
#7 0x000062ff in -[ShowController processFave] at ShowController.m:458
#8 0x002af405 in -[UIApplication sendAction:to:from:forEvent:]
#9 0x00312b4e in -[UIControl sendAction:to:forEvent:]
#10 0x00314d6f in -[UIControl(Internal) _sendActionsForEvents:withEvent:]
#11 0x00313abb in -[UIControl touchesEnded:withEvent:]
#12 0x002c8ddf in -[UIWindow _sendTouchesForEvent:]
#13 0x002b27c8 in -[UIApplication sendEvent:]
#14 0x002b9061 in _UIApplicationHandleEvent
#15 0x02566d59 in PurpleEventCallback
#16 0x01e83b80 in CFRunLoopRunSpecific
#17 0x01e82c48 in CFRunLoopRunInMode
#18 0x02565615 in GSEventRunModal
#19 0x025656da in GSEventRun
#20 0x002b9faf in UIApplicationMain
#21 0x00002498 in main at main.m:14

如果它不是孤立的,以一定範圍內的NSNumbers,我認爲我搞砸了的東西與我的內存管理,但我只是有不知道。

任何想法?

謝謝,
約什

+8

這是因爲ObjC有triskaidekaphobia:p。 – kennytm 2010-03-28 16:16:43

回答

11

數字0到12是特殊的,因爲我在回答另一個問題時發現了here。請記住,這是一個實現細節,而不是語言規範的事情。

基本上,數字(包括)12給你一個已經存在的NSNumber的引用,這是可能的,因爲它們是不可變的。調查顯示,13人或更多的數字給出了一個單獨的例子。

因此,你可能搞砸你的內存管理畢竟:-)這只是,事實上,數字少於13可能引用已存在的數字,在這種情況下保存您的燻肉。我建議你發佈更多的代碼,以便我們可以追蹤到具體問題。


而基於這裏另一個答案您的評論:

我加了一個保持線路到代碼和現在的一切完美的作品。不知道爲什麼。我只是想和它一起滾動。謝謝!

我想你會發現這樣一個事實,NSNumbers小於13已經有你自己之前保持的1計數(碰撞向上計數2)他們爲什麼不造成EXC_BAD_ACCESS。很明顯,你的代碼正在丟失你分配的數字,但系統並沒有釋放那些在13以下的數據,因爲它們仍在使用中(保留1或更多)。

+1

迷人!像「數字0到12是特殊的」這樣的陳述是不可能沒有經過測試的,而且羅和看,你是絕對正確的! :) – 2010-03-28 16:41:37

+0

哇。這是錯誤的。這是我對Objective-C非常討厭的事情之一。所有數字都應該是不可變的。所有字符串都應該是不可變的。 Python得到了這個權利。 – vy32 2010-03-29 06:22:31

+0

在那裏,@ vy32,我認爲你的答案是「這麼錯了」,而不是ObjC的行爲。 :-)但我不確定我瞭解你。 NSNumbers確實是不可變的,這就是使得這種優化成爲可能的原因(例如,你不能改變NSNumber(15)後面的數字來使其他人使用它)。 – paxdiablo 2010-03-29 07:00:20

2

顯然NSNumbers> 12將保留。我建議你寫一個非常小的程序來證明這一點。然後採取該程序,使其成爲一種功能,並在程序中儘早調用它。慢慢地將該功能移到程序中以後的點,直到出現錯誤。你會因此找到你真正的錯誤。

+0

我在代碼中添加了一個保留行,現在一切正常。不知道爲什麼。我只是想和它一起滾動。 謝謝! – jkap 2010-03-28 15:20:20

+0

@jkap我是否可以建議研究內存管理規則並找出它爲什麼現在可行?如果你明白你是如何解決這個問題的,那麼未來你將不會有類似的問題。 – 2010-03-28 15:29:49

+1

@jkap:將隨機保留添加到您的代碼中會導致您無法釋放的程序泄漏大量內存。保留/釋放規則實際上非常清晰,一旦你得到了他們的幫助,所以花時間去了解發生了什麼。 – Felixyz 2010-03-28 18:41:29