ios 关于深拷贝、浅拷贝的思考

在做demo的过程中,遇到了一个问题。

 (A页面)

(B页面)

在A页面点击“编辑信息”之后,跳转到B页面。在B编辑页面中,修改“备注”项,但是没点“保存”提交修改信息,而是点的导航栏的左返回按键回到A界面。

下次在A界面再点击“编辑信息”,跳转B,备注栏原本应该显示“123”,却错误的显示“123345”。

界面间我是用的model传值。

看了深拷贝、浅拷贝相关原理之后,大概知道原因了。区别深浅拷贝的唯一标准就是:对象地址是否相同,如果相同,就是浅拷贝,反之则为深拷贝。这里的surveyModel是用的浅拷贝,指向同一地址,所以B的model改变了,A的也会改变。

所以需要深拷贝surveyModel,使得同样内容,但是指向另一地址。

因为Foundation框架下的类,并不是所有的都支持深拷贝、浅拷贝,只有那些遵循了NSCopying 或者 NSMultableCopying 协议的类,才可以进行拷贝操作。所以修改model,遵守NSCopying协议,然后.m文件中写copywithzone方法。

-(id)copyWithZone:(NSZone *)zone {
    SurveyModel *model = [[SurveyModel allocWithZone:zone] init];
    model.surveyId = self.surveyId;
    model.surveyTitle = [self.surveyTitle mutableCopy];
    model.surveyAuthor = self.surveyAuthor;
    model.surveyDate = self.surveyDate;
    model.updateDate = self.updateDate;
    model.surveySource = [self.surveySource mutableCopy];
    model.surveyRemark = [self.surveyRemark mutableCopy];
    model.surveyDescribe = [self.surveyDescribe mutableCopy];    
    return model;
}

并修改界面传值。

这样的话属性值就不会发生不想要的改变了。

附:

multableCopy 方法是执行深拷贝。如果该对象是容器类型,那么,返回的对象是深拷贝后的对象,但是这个对象里元素,还是之前对象里的元素,地址并没有变化。如果希望深拷贝后,返回的容器类型的对象里的元素也是深拷贝类型的,那么需要对容器内的元素也执行拷贝方法。

copy并不一定是浅拷贝,copy出来的一定是不可变字符串或者数组。如果被拷贝的对象是可变数组或者字符串,这时候会发生深拷贝,反之则是浅拷贝。

对于可变对象,使用copy或者mutableCopy都是深拷贝。

对于不可变对象,copy方法是浅拷贝, mutableCopy是深拷贝。

猜你喜欢

转载自blog.csdn.net/always_Kyathe/article/details/86534066