iOS Swift:如何避免共享处理类中修改主对象时同步变更单数据的问题
iOS Swift:如何避免共享处理类中修改主对象时同步变更单数据的问题
看起来你遇到了值类型和引用类型混淆的问题,不过先仔细拆解你的代码——其实按你给出的代码逻辑,singleData不应该跟着mainObject.data的修改而变化,因为你用的Int是Swift的值类型,赋值时默认就是值拷贝而非引用传递。我来一步步帮你理清问题,再给出明确的解决方案:
先搞清楚你的代码逻辑误区
你的kOBJECT是结构体(值类型),里面的data是[Int](同样是值类型)。当你执行HandlerClass.shared.mainObject.data[indexPath.row] = 10000时,Swift的底层逻辑是:
- 先拷贝一份
mainObject的结构体实例 - 对拷贝后的实例的
data数组进行修改(数组是值类型,修改元素会生成新的数组实例) - 把修改后的结构体重新赋值回
mainObject
而你之前赋值给singleData的是mainObject.data[indexPath.row]的值拷贝,所以理论上不管后续怎么修改mainObject里的数组元素,singleData都会保持原来的数值,不会被同步修改。
那为什么你会看到singleData跟着变呢?可能是这几个原因:
- 你测试时的其他逻辑干扰了结果
- 实际代码里的
data元素不是Int这种值类型,而是引用类型的对象(比如自定义class) - 代码里的
kOBJECT的data是let属性(你给出的代码里确实是let),这时候你根本无法修改data的元素,这应该是笔误,需要把data改成var才能修改:
struct kOBJECT { let name: String var data: [Int] // 改成var才能修改数组元素 }
确保彻底解耦的正确做法
情况1:元素是值类型(如Int、String、结构体)
值类型的特性就是赋值即拷贝,所以你之前尝试的代码:
let tempValue = HandlerClass.shared.mainObject.data[indexPath.row] HandlerClass.shared.singleData = tempValue
完全正确,和直接HandlerClass.shared.singleData = HandlerClass.shared.mainObject.data[indexPath.row]效果一致,都是值拷贝,不会产生任何引用关联,修改原数组元素不会影响singleData。
情况2:元素是引用类型(如自定义Class)
如果你的实际场景中,data的元素是引用类型,那就要通过深拷贝来断开引用关联。比如自定义一个可拷贝的类:
class CustomDataClass: NSCopying { var value: Int init(value: Int) { self.value = value } // 实现NSCopying协议,完成深拷贝 func copy(with zone: NSZone? = nil) -> Any { return CustomDataClass(value: self.value) } }
然后赋值singleData时,使用拷贝后的实例:
if let originalItem = HandlerClass.shared.mainObject.data[indexPath.row] as? CustomDataClass { HandlerClass.shared.singleData = originalItem.copy() as? CustomDataClass }
总结
- 对于值类型,直接赋值就会自动完成值拷贝,天然解耦,不需要额外操作
- 对于引用类型,必须手动实现拷贝逻辑,通过深拷贝来断开原对象和拷贝对象的引用关联
备注:内容来源于stack exchange,提问作者INFINITE
相关产品推荐
相关产品推荐

