当前位置: 首页 > news >正文

JavaScript 深拷贝方法总结

前情提要

最近在调uni-app时,经常遇到需要深拷贝对象的情况,今天正好有空,给大家博主用到的深拷贝的方法。

最常用的序列化方法

这个是博主最常用的方法,也是个人认为最简洁方便的的,唯一的确定就是部分特殊类型会拷贝失效,总结如下
优点: 简单快捷,兼容性好
缺点: 无法处理 undefined、function、Symbol 类型、Date 对象(转为 ISO 字符串)、正则表达式(转为空对象)

<html>
<style></style>
<body></body>
<script>
	const obj = { a:undefined, b:{b1:1}, c:'测试', d:new Date(), f:function(){} };
	const newObj = JSON.parse(JSON.stringify(obj));
	// 输出 {b:{b1: 1}, c:"测试", d:"2025-04-11T09:16:12.039Z"}
	console.log(newObj)
</script>
</html>

原生方法structuredClone

该方法是HTML5新推出,相比序列化方法,支持了更多数据类型,且更简便了,但是兼容性较差,总结如下
优点: 浏览器原生方法,支持更多数据类型(undefined、Date 对象等)
缺点: 不支持函数、DOM 节点等,且对兼容性有要求,需较新浏览器

<html>
<style></style>
<body></body>
<script>
	const obj = { a:undefined, b:{b1:1}, c:'测试', d:new Date() };
	const newObj = structuredClone(obj);
	// 输出 {a:undefined, b:{b1: 1}, c:"测试", d: Fri Apr 11 2025 17:19:31 GMT+0800 (中国标准时间)}
	console.log(newObj)
</script>
</html>

MessageChannel 异步拷贝

该方法是通过信道通信间的传输,来实现对象的深度拷贝,能处理大部分数据类型,唯一的缺点就是需要异步操作
优点: 能处理除了函数外的大部分数据类型
缺点: 需要异步操作,会增加代码的复杂性

<html>
<style></style>
<body></body>
<script>
	const obj = { a:undefined, b:{b1:1}, c:'测试', d:new Date() };
	function deepClone(obj) {
	  return new Promise(resolve => {
	    const { port1, port2 } = new MessageChannel()
	    port2.onmessage = ev => resolve(ev.data)
	    port1.postMessage(obj)
	  })
	}
	deepClone(obj).then(newObj=>{
		// 输出 {a:undefined, b:{b1: 1}, c:"测试", d: Fri Apr 11 2025 17:19:31 GMT+0800 (中国标准时间)}
		console.log(newObj)
	})
</script>
</html>

自定义方法

最后一种就是我们自己写的方法了,具体总结如下
优点: 可自定义处理特殊类型
缺点: 需要手动处理各种数据类型(Date/RegExp/Map/Set等),性能较差(大数据量时)

<html>
<style></style>
<body></body>
<script>
	const obj = { a:undefined, b:{b1:1}, c:'测试', d:new Date() };
	function deepClone(obj, map = new WeakMap()) {
	  if (obj === null || typeof obj !== 'object') return obj
	  if (map.has(obj)) return map.get(obj)
	  
	  let clone = Array.isArray(obj) ? [] : {}
	  map.set(obj, clone)
	  
	  for (let key in obj) {
	    if (obj.hasOwnProperty(key)) {
	      clone[key] = deepClone(obj[key], map)
	    }
	  }
	  return clone
	}
	const newObj = deepClone(obj);
	// 输出 {a:undefined, b:{b1: 1}, c:"测试", d: Fri Apr 11 2025 17:19:31 GMT+0800 (中国标准时间)}
	console.log(newObj)
</script>
</html>

总结

博主能力有限,基本就只能总结这四种了,大家也可以选择第三方库去实现对象之间的深拷贝,或者有什么其他方法都可评论讨论。

相关文章:

  • HTML应用指南:利用GET请求获取全国德克士门店位置信息
  • 笔试强训题(8)
  • 从零实现HTTP服务器
  • Quartz修仙指南:从定时任务萌新到调度大能的终极奥义
  • 题目 2701: 蓝桥杯2022年第十三届决赛真题-取模(C/C++/Java组)
  • 计算机网络-传输层基础概念
  • 【5】深入学习npm-Nodejs开发入门
  • 【Amazon EC2】为何基于浏览器的EC2 Instance Connect 客户端连接不上EC2实例
  • 第一个Qt开发的OpenCV程序
  • 关税扰动下市场波动,如何寻找确定性的长期之锚?
  • 一周学会Pandas2 Python数据处理与分析-Pandas2读取CSV
  • 榕壹云无人共享系统:基于SpringBoot+MySQL+UniApp的物联网共享解决方案
  • 可以使用多种AI模型自动化制作web和手机应用软件的利器:bolt.diy
  • (十五)安卓开发中不同类型的view之间继承关系详解
  • 去重新闻数据中重复的正文内容(body 字段),并把唯一的新闻内容保存到一个新的 JSON 文件中
  • Ubuntu 软件卸载与清理终极指南
  • 在项目中,引入【全局异常处理器】
  • Spring IoC深度解析:掌控Bean存储艺术与分层架构的智慧​​
  • 通过代码获取接口文档工具
  • 智膳优选 | AI赋能的智慧食堂管理专家 —— 基于飞书多维表格和扣子(Coze)的智能解决方案
  • 外链代发免费/一键优化清理手机
  • 南宁月嫂网站建设/优化网站快速排名软件
  • 工商局网站查询入口/深圳短视频推广
  • 佛山龙江做网站的/怎么写软文推广
  • 网站模板中文/网络营销pdf
  • 多语言企业网站源码/10常用的网络营销方法