0

カスタム オブジェクトをインスタンス変数に割り当てたい。

コードは次のとおりです。
- MyController.h/.m

#import "CustomData.h"  
@interface MyViewController : NSViewController  
@property (retain) CustomData* theData;  

- (void)aRandomMethod; 

@end

@implementation MyViewController  
@synthetize theData;  

- (void)aRandomMethod {  

   NSData* rawData = [someOtherObject someOtherMethod];

   // option 1
   self.theData = [[CustomData alloc] initWithData:rawData];

   // option 2
   CustomData* _theData = [[Custom alloc] initWithData:rawData];

   // option 3
   self.theData = [[[CustomData alloc] initWithData:rawData] autorelease];

   // option 4
   theData = [[CustomData alloc] initWithData:rawData];

   // ... later code calls some methods on theData or _theData, not useful here.
 }
@end

Xcode で Analyze 機能を実行すると、オプション 1 と 2 については "leaked object not referenced later..." が存在するが、オプション 3 と 4 については存在しないことがautoreleaseわかります。セッター。autoreleaseメソッドで所有するオブジェクトを返すときに使用する必要があることはわかっています。

それぞれの選択肢について、なぜそれが間違っているのか正しいのか説明していただけますか? ありがとう。

4

2 に答える 2

5

オプション1は間違っています。なぜならalloc、そのメソッドでオブジェクトを取得したため、そのメソッドがオブジェクトを所有するようになり、その必要があるからreleaseです。それをプロパティに割り当てると、それはそれであり、それが完了したときにretain期待されます。release

選択肢 2 も同じ理由で間違っています。そのプロパティ部分を取り出しますが、 でオブジェクトを作成したため、そのメソッドでそれallocを呼び出す責任があります。release

オプション 3 は正しいです。autoreleaseプロパティに渡す前にそれを行ったので、メソッドはそれを所有しなくなりました。ここで使用すると、プロパティがチャンスを得る前にrelease壊れてしまうので注意してください。releaseretain

オプション 4 が正しい可能性があります。私はそれをivarに割り当てていると仮定しています。後で dealloc メソッドで ivar を手動で解放する場合にのみ正しいです。ただし、一般的には、プロパティを確認する方が適切です。releaseそうしないと、別の値を割り当てて既存の値を忘れるリスクがあります。

于 2013-04-16T22:17:35.750 に答える
1

オプション 1 と 2 について注意すべき最大のことは、alloc が存在するため、対応するリリースである必要があるということです。

オプション 1 は、本質的に「非表示」です。これは、コンパイラがセッターとゲッターを自動生成するためです。表示されないのは、ドット表記を使用する場合、暗黙的に保持呼び出しを含むセッターを通過することです。したがって、オブジェクトを割り当てて保持し、保持カウントを 2 にします。

したがって、将来的に適切にリリースできるようにするには、システムが後でクリーンアップできるように、自動リリース プールに追加するように指定する必要があります。これにより保持カウントが 1 になり、dealloc メソッドでプロパティを安全に解放できます。

于 2013-04-16T22:21:51.840 に答える