ios – ObjectiveC:使用NSString和__weak与ARC时的奇怪行为

第一个代码和输出:
NSString *text = @"Sunny";
__weak NSString *string0 = text.lowercaseString;
__weak NSString *string1;
string1 = text.lowercaseString;

NSLog(@"%@,%@",string0,string1);

输出:

(null),sunny

但是在我将text1的声明移到文本上方后,输出就不同了.这是代码:

__weak NSString *string1;
NSString *text = @"Sunny";
__weak NSString *string0 = text.lowercaseString;
string1 = text.lowercaseString;

NSLog(@"%@,string1);

输出:

sunny,sunny

我对不同的输出很困惑:

>为什么string0和string1在第一种情况下有所不同?
>为什么第二种情况的输出与第一种情况不同?

解决方法

试图弄清楚对象何时被释放或者弱引用是否具有挑战性,并且通常并不能真正帮助理解.以下是您可以看到与预期不同的结果的一些原因:

> NSString:在进行这类调查时最好不要使用此类型.字符串文字是不朽的,它们不会被收集,即使你不期望它也可能有一个字符串文字.
>自动释放池:自动释放池实际上是ARC之前的宿醉,但它仍然存在,并且许多方法返回自动释放的对象.这意味着许多物体的寿命会超出您的预期,但不会太长.但是,ARC有技巧并且可以尽早从自动释放池中删除对象,因此您可能首先认为该对象将存活更长时间然后它不会…
>弱引用:在前两个子弹之后,您应该猜测,因为您可能不知道对象何时被释放,如果有的话,那么当弱引用被取消时您可能不知道.试想“很快”.
>优化:编译器可以做的优化有一些余地,虽然保留了程序的正确语义,但可能会改变对象的生命周期.

如果您确实希望运行这些调查,那么如果(a)使用您自己的类类型,而不是库中的任何类型,并且(b)使用@autoreleasepool {…}块来限制auto的生命周期,您可能会更进一步.发布的对象.

作为一个例子,当我在编译器上运行你的代码时,我没有得到(null),但是将第一个赋值更改为string0 = text.lowercaseString.mutableCopy确实产生了一个…找出为什么留下作为一个行使…

有一个探究的头脑和探索,这是好的,但要为非显而易见的人做好准备!

HTH

相关文章

当我们远离最新的 iOS 16 更新版本时,我们听到了困扰 Apple...
欧版/美版 特别说一下,美版选错了 可能会永久丧失4G,不过只...
一般在接外包的时候, 通常第三方需要安装你的app进行测...
前言为了让更多的人永远记住12月13日,各大厂都在这一天将应...