我不知道你正在使用的API,所以我不能100%確定發生了什麼。我GOOGLE了,他們似乎是OCMock的一部分。我下載了它(並沒有安裝它,因爲我不感興趣),我迅速瀏覽了源代碼。
我在該代碼中看到一些非常可疑的東西。下面是他們如何實現你所說的第一種方法:
@implementation OCMArg
....
+ (id *)setTo:(id)value
{
return (id *)[[[OCMPassByRefSetter alloc] initWithValue:value] autorelease];
}
因此,他們正在返回的id*
這實際上只是一個id
。對我來說,要麼是廢話/錯誤,要麼是試圖操作ObjC內部(即使沒有記錄,ObjC對象存儲的第一件事實際上是指向對象類的指針,因此類型爲Class
,它與id
,因此它以某種方式有效地將指向對象的指針或指向對象的指針指向Class*
或id*
)。我沒有時間或興趣去研究整個API,找出他們爲什麼這樣做。他們實際上可能有一個很好的理由(例如,如果你只將這個結果傳遞給另一個知道它應該是什麼的API,但你在這裏做的不止這些)。我不會學習OCMock,而是會盡我所能地解釋你所發生的事情(ObjC和ARC)。
id __autoreleasing *arg = [OCMArg setTo:mockData];
ARC在這行代碼中絕對不會做任何事情。
你可以在上面看到那種方法。類OCMPassByRefSetter
是一個簡單的類,只保留它後保存參數,因此保留mockData
。該OCMPassByRefSetter
是自動釋放,並將在下一個消失(釋放mockData
和使*arg
引用釋放的內存)。
注意arg
其實指向OCMPassByRefSetter
(該isa
的isa
是任何對象的「第一」的伊娃,這是Class
類型和指向對象的類的。但是,這是沒有證件,並可以在改變任何時候)。
CFTypeRef expectedResult = (__bridge CFTypeRef) *arg;
*arg
是id
型這與CFTypeRef
兼容的,所以鑄件是有效的。你使用__bridge
,所以ARC絕對沒有。
如果arg
指着一張「收費免費橋」 CF /可可類,這將是完全合法的代碼,但你必須要小心,expectedResult
將在下屆漏失效(這不是retained
,但它是活的一個自動發佈的實例)。
[[[self.mockSecItemService expect] andReturnValue:OCMOCK_VALUE(mockCopyStatus)] copyItemMatching:queryCheck
result:&expectedResult];
不知道這條線是幹什麼的。鑑於您在上面的評論中發佈的原型,ARC在部分result:&expectedResult
上沒有做任何事情。
你說這是一個圍繞SecItemCopyMatching
的包裝,但據我所知它不僅僅是這樣。如果它只是立即呼籲SecItemCopyMatching
通過result:
的論點,你很可能會搞砸了。但名字expectedResult
和事實,這是OCMock讓我覺得這是比這更復雜一點。
你必須自己調查一下。但請記住:
- 只要當前函數退出,您通過的參數(
&expectedResult
)將變爲無效,因爲它是局部變量。
- 只要存在漏極,的值就會變爲無效,因爲該地址指向將由漏極重新分配的存儲器。
- 做任何東西與值
expectedResult
可能會出現非常錯誤的,因爲我不認爲Class
合格爲「免費橋接」。
我懷疑,但我可能是非常錯誤的,你沒有使用OCMock apis的方式,他們打算使用。但在這方面,我無法幫助你,也許你確實做得對。
這是一個bad_access錯誤? – Dustin 2012-08-13 18:05:25
你在發佈'expectedResult'嗎?如果這樣就停下來。 – Joe 2012-08-13 18:14:02
我收到一個bad_access錯誤,但我沒有發佈expectedResult。 – Eric 2012-08-13 18:15:30