我知道,这是基本的东西。但我一直对此感到困惑。
所以假设我有一个叫做HolderClass的类,它有一个名为changeMe的NSString属性。
我有另一个名为PassedToClass的类,它有一个方法,它将HolderClass的一个实例作为参数,在该方法中,它使用HolderClass的实例来设置一个名为holderInsideOtherClass的属性。
我要将holderClass的实例传递给PassedToClass的实例,如下所示:
HolderClass *demonstrationHolder= [HolderClass new];
PassedToClass *passToMe = [PassedToClass new];
demonstrationHolder.changeMe = @"FirstString";
[passToMe arbitraryMethodThatTakesAHolderClass: demonstrationHolder];
现在,完成此操作后,我可以在两个类中检查changeMe的值:
NSLog (@"%@", demonstrationHolder.changeMe);
NSLog (@"%@", passToMe.holderInsideOtherClass.changeMe);
这两个都应该打印出“FirstString”。
但是现在,如果我这样做会发生什么:
[demonstrationHolder.changeMe = @"SecondString"];
NSLog (@"%@", demonstrationHolder.changeMe);
NSLog (@"%@", passToMe.holderInsideOtherClass.changeMe);
我知道我应该知道这一点,但任何人都可以帮忙吗?
答案 0 :(得分:3)
保存对象的变量只是指针(内存地址)。当您传递它们或将它们分配给其他变量时,您仍然在完全相同的内存位置引用完全相同的对象。
因此,当您将demonstrationHolder
传递到passToMe
时,passToMe
只会获得对原始对象的引用。如果您将任意位置更改为特定对象,那么这些更改将显示每个包含对该特定对象的引用的代码。这是同一个目标。
当处理可以这种方式改变的对象(“可变”对象)时,通常将属性定义为copy
而不是assign
/ retain
/ {{1 }}。在这种情况下,您将对象分配给该属性,而不是简单地存储引用,而是创建一个新对象,该对象是原始对象的副本,而是存储对新对象的引用。这意味着将来对原始对象的任何更改都不会影响新副本。
答案 1 :(得分:0)
HolderClass *demonstrationHolder= [HolderClass new];
当执行这行代码时,将为HolderClass
的一个实例分配内存,并为该实例指定一个指针(HolderClass *
),并将其指定给{{1} }。
获得指针后,您将其分配给demonstrationHolder
实例中的成员:
passToMe
这仍然是由[passToMe arbitraryMethodThatTakesAHolderClass: demonstrationHolder];
表示的相同指针值;它只是一个存储位置,其中存在真实的demonstrationHolder
实例。
HolderClass
因为两个指针([demonstrationHolder.changeMe = @"SecondString"];
和demonstrationHolder
)指向同一个实例,当您使用它们中的任何一个来访问passToMe.holderInsideOtherClass
的实例时,您正在修改同一个对象记忆。因此:
HolderClass
这两行都会记录NSLog (@"%@", demonstrationHolder.changeMe);
NSLog (@"%@", passToMe.holderInsideOtherClass.changeMe);
。