屋稷删 发表于 2026-1-20 21:25:00

new JSONObject(original) 是浅拷贝

​最近做一个功能的时候,想复制一个 JSONObject 里的所有属性,就直接使用的 new JSONObject(original),之后对新new的和老的 JSONObject 进行了一些操作,然后落库,发现落库的数据总是有问题,怪怪的。最后发现 new JSONObject(original) 出来的JSONObject和老的JSONObject是 共享 的属性。故此记录一下。
我这里使用的是 alibaba 的 com.alibaba.fastjson.JSONObject。
我们先说说什么是 深拷贝?什么是 浅拷贝?
深拷贝:深拷贝是指创建一个新的对象,并递归地复制原始对象中的所有引用类型数据结构,包括内部的对象。深拷贝后的对象与原始对象 完全独立,对其中一个对象的修改 不会影响 另一个对象。
浅拷贝:浅拷贝是指创建一个新的对象,该对象的内容是原始对象的副本。如果原始对象中包含了引用类型的数据结构(如列表、字典等),浅拷贝只会复制这些引用,而不会复制引用指向的对象本身。因此,原始对象和浅拷贝后的对象会 共享 一些内部对象的引用,修改其中一个对象的共享部分 可能会影响 另一个对象。(这个知识点,我在之前的博文里提及过了,自己用的时候也搞忘了)
浅拷贝 —— 修改新 JSONObject,原对象也会被修改:
public static void main(String[] args) {      // 原始对象      JSONObject original = new JSONObject();      original.put("name", "张三");      // 原始对象中的嵌套对象      JSONObject address = new JSONObject();      address.put("city", "北京");      address.put("street", "长安街");      original.put("address", address);      // 使用构造函数"拷贝"      JSONObject copy = new JSONObject(original);      copy.put("name", "李四");      // 修改浅拷贝后对象的嵌套内容      copy.getJSONObject("address").put("city", "上海");      System.out.println("原始对象: " + original);      System.out.println("拷贝对象: " + copy);      System.out.println("address是否同一个对象: " + (original.get("address") == copy.get("address")));      // 输出结果:      // 原始对象: {"address":{"city":"上海","street":"长安街"},"name":"李四"}      // 拷贝对象: {"address":{"city":"上海","street":"长安街"},"name":"李四"}      // address是否同一个对象: true (证明是浅拷贝)    }后来我调整了代码,使用 序列化 来实现深拷贝:
public static void main(String[] args) {      // 原始对象      JSONObject original = new JSONObject();      original.put("name", "张三");      // 原始对象中的嵌套对象      JSONObject address = new JSONObject();      address.put("city", "北京");      address.put("street", "长安街");      original.put("address", address);      // 深拷贝:先序列化为JSON字符串,再反序列化为新对象      String jsonStr = original.toJSONString();      JSONObject deepCopy = JSONObject.parseObject(jsonStr);      deepCopy.put("name", "李四");      // 修改深拷贝后的子对象      deepCopy.getJSONObject("address").put("city", "上海");      System.out.println("原始对象: " + original);      System.out.println("拷贝对象: " + deepCopy);      System.out.println("address是否同一个对象: " + (original.get("address") == deepCopy.get("address")));      // 输出结果:      // 原始对象: {"address":{"city":"北京","street":"长安街"},"name":"张三"}      // 拷贝对象: {"address":{"city":"上海","street":"长安街"},"name":"李四"}      // address是否同一个对象: false (证明是深拷贝)    }当我们在上下文中使用JSON对象时,总是假设需要深拷贝,除非我们能明确使用浅拷贝是符合需求,跟我们想要的结果是一致的。
业精于勤荒于嬉,行成于思毁于随。-- 烟沙九洲

来源:程序园用户自行投稿发布,如果侵权,请联系站长删除
免责声明:如果侵犯了您的权益,请联系站长,我们会及时删除侵权内容,谢谢合作!

揿纰潦 发表于 2026-2-1 05:53:29

喜欢鼓捣这些软件,现在用得少,谢谢分享!

段干叶农 发表于 2026-2-4 05:56:05

用心讨论,共获提升!

昝琳怡 发表于 2026-2-6 07:27:43

收藏一下   不知道什么时候能用到

端木茵茵 发表于 2026-2-8 00:51:31

鼓励转贴优秀软件安全工具和文档!

啖曼烟 发表于 2026-2-11 06:09:06

感谢分享

柏球侠 发表于 2026-2-11 20:39:06

不错,里面软件多更新就更好了

阙忆然 发表于 2026-2-13 19:30:09

热心回复!

叟澡帅 发表于 2026-2-19 03:19:40

谢谢分享,试用一下

姥恫 发表于 2026-2-22 06:59:50

分享、互助 让互联网精神温暖你我

章娅萝 发表于 2026-2-25 10:24:09

新版吗?好像是停更了吧。

喜及眩 发表于 2026-2-26 13:32:03

这个好,看起来很实用

溜椎干 发表于 2026-2-27 03:46:27

很好很强大我过来先占个楼 待编辑

怒鼓踊 发表于 2026-2-28 04:28:38

新版吗?好像是停更了吧。

归筠溪 发表于 2026-3-8 06:35:05

这个好,看起来很实用

印萍 发表于 2026-3-10 17:05:22

谢谢楼主提供!
页: [1]
查看完整版本: new JSONObject(original) 是浅拷贝