如果在 Objective-C 中使用手动内存管理,赋值不会改变对象的保留计数。你肯定会使用它,否则,你不能release
在你的代码中调用方法。
因此,您的代码执行以下操作。它创建NSString
保留计数 = 1 的对象,并将其分配给string1
指针。之后,您分配string1
给string2
. 现在你有 2 个指向同一个对象的指针,并且这个对象的保留计数仍然是 1。然后你释放对象,它立即被释放。之后您遇到崩溃:
NSString * string1 = [[NSString alloc]initWithFormat:@"hello"]; // string retain count is 1
string2 = string1; // 2 pointers to same string, retain count is still 1
[string1 release]; // string is deallocated when retain count drops to 0
NSLog(@"string2 = %@", string2); // here app is crashing
要解决这个问题,您可以retain
在做作业时使用。
NSString * string1 = [[NSString alloc]initWithFormat:@"hello"]; // string retain count is 1
string2 = [string1 retain]; // 2 pointers to same string, retain count is 2
[string1 release]; // string retain count back to 1
NSLog(@"string2 = %@", string2); // no crash
此外,您可以使用copy
. 请注意, for NSString
copy 实际上并不复制对象,它只是调用retain
. 无需执行实际复制,因为NSString
它是不可变的,无法更改。如果我们使用NSMutableString
,事情将会改变:
NSMutableString * string1 = [[NSMutableString alloc]initWithFormat:@"hello"]; // string retain count is 1
NSMutableString * string2 = [string1 copy]; // 2 separate strings, both have retain count 1
[string1 release]; // string1 is deallocated
NSLog(@"string2 = %@", string2); // no crash, string2 retain count is 1
或者,您可以使用 ARC。它将在编译时插入相应的保留/释放调用。然后代码将如下所示:
NSString * string1 = [[NSString alloc]initWithFormat:@"hello"];
string2 = string1;
string1 = nil;
NSLog(@"string2 = %@", string2); // no crash
我建议先了解手动内存管理,然后再迁移到 ARC。