什么是深拷贝

710 字
4 分钟
什么是深拷贝

1. 什么是浅拷贝?#

浅拷贝只创建一个新的最外层对象,内部嵌套对象仍然与原对象共用。

例如:

const original = {
taskName: "市场分析",
user: {
name: "Alice"
}
};
const copy = { ...original };

此时:

original copy
│ │
├─ taskName ├─ taskName
│ │
└──────┐ ┌─────┘
↓ ↓
同一个 user 对象

修改最外层字段通常互不影响:

copy.taskName = "行业分析";
console.log(original.taskName);
// "市场分析"

但是修改嵌套对象会影响原对象:

copy.user.name = "Bob";
console.log(original.user.name);
// "Bob"

原因是 copy.user 和 original.user 指向同一份内存数据。


2. 什么是深拷贝?#

深拷贝不仅复制最外层对象,还递归复制内部所有嵌套对象和数组。

const deepCopy = structuredClone(original);

可以理解为:

original deepCopy
│ │
└─ user 对象 A └─ user 对象 B
对象 A 和对象 B 内容相同,但彼此独立

现在修改副本:

deepCopy.user.name = "Carol";
console.log(original.user.name);
// 不会变成 "Carol"

因此,并行任务各自拿到深拷贝后,即使修改嵌套内容,也不会直接影响原始 Context 或其他任务的副本。


3. 浅拷贝和深拷贝的区别#

假设原数据是:

const context = {
step: 1,
data: {
items: ["A", "B"]
}
};

3.1 浅拷贝#

const copy = { ...context };
copy.data.items.push("C");

结果可能是:

context.data.items
// ["A", "B", "C"]

虽然修改的是 copy,但原数据也变了,因为嵌套的 data 和 items 仍然共享。

3.2 深拷贝#

const copy = structuredClone(context);
copy.data.items.push("C");

结果是:

context.data.items
// ["A", "B"]
copy.data.items
// ["A", "B", "C"]

二者已经完全独立。

对比浅拷贝深拷贝
最外层对象独立独立
嵌套对象和数组通常共享独立
修改嵌套数据可能影响原数据不影响原数据
性能和内存开销较小较大
适合情况数据严格只读或结构简单任务确实需要修改副本

4. 为什么“浅拷贝 + 只读”也可以安全?#

这是我们在步骤并行化里提到过的做法。虽然浅拷贝仍然共享嵌套对象,但只要所有并行任务都遵守:

可以读取,不可以修改

就不会发生并发覆盖。例如:

// 安全:只读取
const count = localContext.searchResults.length;
// 不安全:修改了共享的嵌套数组
localContext.searchResults.push(newResult);

所以常见设计是:

前序数据:不可变,只允许读取
并行步骤的新结果:通过 return 单独返回
调度器:等待步骤结束后统一合并

这通常比给每个任务深拷贝一份大型 Context 更节省内存和时间。

总之:

前序数据是并行步骤开始前,上游已经确定的共享输入;浅拷贝只复制外壳,内部数据仍可能共享;深拷贝连内部嵌套数据也复制,因此副本之间更加独立,但成本也更高。

文章分享

如果这篇文章对你有帮助,欢迎分享给更多人!

什么是深拷贝
https://hac.he.cn/posts/agent-03/
作者
HAC
发布于
2026-08-28
许可协议
CC BY-NC-SA 4.0

评论区

Profile Image of the Author
HAC
观之非易,行且克难
Greetings
欢迎来到我的博客!这里主要分享我的学习笔记与兴趣爱好。
音乐
封面

音乐

暂未播放

0:000:00
暂无歌词
分类
标签
站点统计
文章
46
分类
8
标签
19
总字数
116,126
运行时长
0 天
最后活动
0 天前
文章目录