内存泄漏时保留财产
我正在尝试在每个button上单击我的应用程序发出一个点击声音为此,我创build了一个实用程序类的.h和.m如下
.h文件
@interface SoundPlayUtil : NSObject<AVAudioPlayerDelegate,AVAudioSessionDelegate> { AVAudioPlayer *audioplayer; } @property (retain, nonatomic) AVAudioPlayer *audioplayer; -(id)initWithDefaultClickSoundName; -(void)playIfSoundisEnabled; @end
.m文件
@implementation SoundPlayUtil @synthesize audioplayer; -(id)initWithDefaultClickSoundName { self = [super init]; if (self) { NSString* BS_path_blue=[[NSBundle mainBundle]pathForResource:@"click" ofType:@"mp3"]; self.audioplayer =[[AVAudioPlayer alloc]initWithContentsOfURL:[NSURL fileURLWithPath:BS_path_blue] error:NULL]; [self.audioplayer prepareToPlay]; } return self; } -(void)playIfSoundisEnabled { if ([[NSUserDefaults standardUserDefaults] boolForKey:soundStatus]==YES) { [self.audioplayer play]; } } -(void)dealloc { [audioplayer release]; [super dealloc]; } @end
并在button上点击我正在做的任何课程
SoundPlayUtil *obj = [[SoundPlayUtil alloc] initWithDefaultClickSoundName]; [obj playIfSoundisEnabled]; [obj release];
它的工作正常,我成功地播放声音。 当我分析代码时出现问题。 编译器显示在实用程序类的.m中的initWithDefaultClickSoundName方法中存在内存泄漏,因为我正在将alloc方法发送到self.audioplayer,而不是释放它。
释放这个对象的最好的地方是什么?
问题是,当你分配的对象是retainCount将是1,你将该对象分配给一个retain属性对象。 然后它将再次保留该对象,因此retainCount将是2。
保留属性的setter代码如下所示:
- (void)setAudioplayer: (id)newValue { if (audioplayer != newValue) { [audioplayer release]; audioplayer = newValue; [audioplayer retain]; } }
更改:
self.audioplayer =[[AVAudioPlayer alloc]initWithContentsOfURL:[NSURL fileURLWithPath:BS_path_blue] error:NULL];
喜欢;
self.audioplayer =[[[AVAudioPlayer alloc]initWithContentsOfURL:[NSURL fileURLWithPath:BS_path_blue] error:NULL] autorelease];
或者像:
AVAudioPlayer *player = [[AVAudioPlayer alloc]initWithContentsOfURL:[NSURL fileURLWithPath:BS_path_blue] error:NULL]; self.audioplayer = player; [player release];
self.audioplayer =[[AVAudioPlayer alloc]initWithContentsOfURL:[NSURL fileURLWithPath:BS_path_blue] error:NULL];
在这里,您创build一个新的对象,然后将其分配给一个保留的属性。 但是,除了财产之外,你再也没有提及这个对象,所以它会泄漏。 你已经增加了两次保留计数。
按照优先顺序来修复:
- 转换成ARC;)
-
创build一个局部variables,将其分配给属性,然后释放它。
Object *object = [[Object alloc] init]; self.property = object; [object release];
-
self.property = [[[Object alloc] init] autorelease];
添加一个autorelease调用对象self.property = [[[Object alloc] init] autorelease];