JavaScript新特性structuredClone()深拷贝策略详解

 更新时间:2025年06月04日 09:46:43   作者:watermelo37  
structuredClone()是浏览器和Node.js的原生API,底层使用更高效的 C++ 实现,比起JS层的JSON.stringify/parse 组合,性能通常更好,这篇文章给大家介绍JavaScript新特性structuredClone()深拷贝策略,感兴趣的朋友一起看看吧

JavaScript新特性structuredClone(),一行代码优化深拷贝策略

structuredClone()使用起来非常简单:

const cloned = structuredClone(obj);

替代:

const cloned = JSON.parse(JSON.stringify(obj));

想知道structuredClone()除了深拷贝以外,还有哪些JSON.parse(JSON.stringify(obj))所没有的功能吗?比起JSON.parse(JSON.stringify(obj))有什么性能上的提升吗?structuredClone()的环境限制有哪些?

本文会告诉你答案。

一、structuredClone()介绍

1、structuredClone()是什么

structuredClone() 是浏览器和 Node.js 的原生 API,底层使用更高效的 C++ 实现,比起 JS 层的 JSON.stringify/parse 组合,性能通常更好。

在结构复杂/嵌套多时差异更明显,不需要转成字符串再解析,避免了冗余的编码/解码过程。

2、structuredClone()环境支持

在 Node.js 17+、Chrome 98+、Firefox 94+ 中支持。

3、structuredClone()不会拷贝的内容

不支持或无法克隆的类型/结构说明
函数 (Function)无法克隆函数或方法
SymbolSymbol 属性会被忽略
类实例的方法/原型链原型链不会保留,克隆后不是原类的实例
DOM 节点(如 Element、Node)不支持 DOM 对象(比如浏览器中的 HTML 元素)
Proxy 对象无法克隆代理对象(Proxy
WeakMap / WeakSet因其不可枚举和弱引用特性,无法被克隆
函数作用域内的闭包变量本质上函数不能克隆,因此也无法保留闭包
不可序列化的 host 对象如浏览器特有的某些对象(如 Window, FileList

4、基础案例

structuredClone()支持Map、Set、Blob、Date、File等JSON.parse(JSON.stringify(obj))不支持的类型:

const original = {
// 原始类型
string: 'Hello',
number: 123,
boolean: true,
null: null,
undefined: undefined, // JSON会丢失,structuredClone保留
// 日期对象 (JSON会转为字符串,structuredClone保持为Date对象)
date: newDate('2023-06-15'),
// 正则表达式 (JSON会转为空对象,structuredClone保持为RegExp对象)
regex: /pattern/g,
// 集合类型
map: newMap([['key', 'value']]),
set: newSet([1, 2, 3]),
// 二进制数据
arrayBuffer: newUint8Array([1, 2, 3]).buffer,
typedArray: newUint8Array([1, 2, 3]),
// 嵌套数组和对象
array: [1, 2, { nested: true }],
object: { nested: { deep: true } }
};
const clone = structuredClone(original);
// 验证类型保持一致
console.log(clone.date instanceof Date);        // true
console.log(clone.regex instanceof RegExp);     // true
console.log(clone.map instanceof Map);          // true
console.log(clone.set instanceof Set);          // true
console.log(clone.arrayBuffer instanceof ArrayBuffer); // true
console.log(clone.typedArray instanceof Uint8Array);  // true
const clone2 = JSON.parse(JSON.stringify(original));
console.log(clone2.date instanceof Date); // false (变成字符串)
console.log(clone2.set instanceof Set); // false (变成数组)

5、structuredClone()的兼容性判断

可以用如下代码安全使用 structuredClone(),在不支持的环境里自动回退到 JSON 方案(虽然功能会弱一些):

function deepClone(obj) {
  if (typeof structuredClone === 'function') {
    return structuredClone(obj);
  } else {
    // fallback: JSON 克隆(注意功能有限)
    return JSON.parse(JSON.stringify(obj));
  }
}

二、 structuredClone()比JSON.parse(JSON.stringify(obj))有什么区别

1、对比表格

特性JSON.parse(JSON.stringify(obj))structuredClone(obj)
深拷贝
性能较慢(中间需要序列化+解析)更快(原生实现)
支持循环引用报错支持
支持类型丰富度仅支持普通对象、数组、字符串、数字、布尔、null支持更多类型(Map、Set、Blob、Date、File 等)
丢失信息会丢失函数、undefined、Symbol、日期、原型链等保留更多原始结构
错误处理易错(如循环引用会直接抛错)更安全,报错更明确

2、循环引用

循环引用是对象内部相互引用,形成“闭环”的结构,比如:

const obj = {};
obj.self = obj;
const cloned = structuredClone(obj); 

如果用 JSON.stringify(obj) 就会报错:TypeError: Converting circular structure to JSON。但 structuredClone() 就能正确处理

三、structuredClone()在性能上的提升

根据多个社区实测 benchmark(如 ​JSBench.me​、V8 团队 blog 和真实项目测试):

  • 深层嵌套对象(10层以上):structuredClone() 明显更快;
  • 包含 Map、Set、Date、ArrayBuffer 的复杂对象:structuredClone() 能直接处理,而 JSON 克隆则需要额外转换或报错;
  • 平均测试中 structuredClone() 比 JSON 快 1.5~5 倍,尤其在大型对象上提升更显著。

四、结语

目前,structuredClone() 已被所有主流浏览器支持。它为深拷贝问题提供了一个简单、高效的解决方案,快来拥抱这个JavaScript新特性吧。

到此这篇关于JavaScript新特性structuredClone()深拷贝策略详解的文章就介绍到这了,更多相关js structuredClone()深拷贝内容请搜索脚本之家以前的文章或继续浏览下面的相关文章希望大家以后多多支持脚本之家!

相关文章

  • JavaScript canvas实现俄罗斯方块游戏

    JavaScript canvas实现俄罗斯方块游戏

    这篇文章主要为大家详细介绍了JavaScript canvas实现俄罗斯方块游戏,文中示例代码介绍的非常详细,具有一定的参考价值,感兴趣的小伙伴们可以参考一下
    2021-07-07
  • 深入理解JavaScript系列(31):设计模式之代理模式详解

    深入理解JavaScript系列(31):设计模式之代理模式详解

    这篇文章主要介绍了深入理解JavaScript系列(31):设计模式之代理模式详解,代理模式使得代理对象控制具体对象的引用,代理几乎可以是任何对象:文件,资源,内存中的对象,或者是一些难以复制的东西,需要的朋友可以参考下
    2015-03-03
  • 详解如何在Canvas上实现坐标定位

    详解如何在Canvas上实现坐标定位

    这篇文章我们将来详细的给大家讲解一下如何在 canvas 上实现坐标的定位,文中有详细的代码示例供大家参考,具有一定的参考价值,需要的朋友可以参考下
    2023-08-08
  • javascript中文本框中输入法切换的问题

    javascript中文本框中输入法切换的问题

    这篇文章主要是对javascript中文本框中输入法切换的问题进行了详细的分析介绍,需要的朋友可以过来参考下,希望对大家有所帮助
    2013-12-12
  • javascript form 验证函数 弹出对话框形式

    javascript form 验证函数 弹出对话框形式

    javascript合法验证 js数据验证、js email验证、js url验证、js长度验证、js数字验证等(弹出对话框形式)
    2009-06-06
  • 小程序自定义tabBar组件封装

    小程序自定义tabBar组件封装

    这篇文章主要为大家详细介绍了小程序自定义tabBar组件封装,文中示例代码介绍的非常详细,具有一定的参考价值,感兴趣的小伙伴们可以参考一下
    2021-11-11
  • javascript内置对象操作详解

    javascript内置对象操作详解

    这篇文章主要介绍了javascript内置对象操作详解,需要的朋友可以参考下
    2015-02-02
  • javascript整除实现代码

    javascript整除实现代码

    javascript实现整除的实现代码,需要的朋友可以参考下。
    2010-11-11
  • 原生JS实现记忆翻牌游戏

    原生JS实现记忆翻牌游戏

    这篇文章主要为大家详细介绍了原生JS实现记忆翻牌游戏,文中示例代码介绍的非常详细,具有一定的参考价值,感兴趣的小伙伴们可以参考一下
    2020-07-07
  • layui 图片上传+表单提交+ Spring MVC的实例

    layui 图片上传+表单提交+ Spring MVC的实例

    今天小编就为大家分享一篇layui 图片上传+表单提交+ Spring MVC的实例,具有很好的参考价值,希望对大家有所帮助。一起跟随小编过来看看吧
    2019-09-09

最新评论