You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

JavaScript问题:为何修改新数组元素属性会影响原数组?

为什么修改slice()复制的数组元素属性会影响原数组?

嘿,这个问题其实是JavaScript里浅拷贝和深拷贝的典型区别,我来给你掰扯清楚~

首先得明确:slice()方法确实会创建一个新数组,但它做的是浅拷贝。也就是说,新数组本身是独立的,但如果数组里的元素是对象、数组这类引用类型,新数组存的只是原数组元素的内存引用——简单说,两个数组里的对应对象其实指向内存里的同一个东西。

咱们拆分你遇到的两种情况来看:

  • 替换整个数组元素:比如newHeroes[0] = {name: 'Test 1'},这时候你是给新数组的第一个位置重新赋值了一个全新的对象引用,原数组的第一个元素还是指向原来的那个对象,所以原数组完全不受影响,这和你预期的一致。
  • 直接修改元素属性:比如newHeroes[1].name = 'Test 2',这时候你并没有改变新数组里这个元素的引用,而是顺着这个引用去修改了它指向的那个对象的属性。因为原数组的heroes[1]和新数组的newHeroes[1]指向的是内存里同一个对象,所以这个修改会同时反映在两个数组里。

给你贴个简单的代码示例直观感受下:

const heroes = [{name: 'Iron Man'}, {name: 'Captain America'}];
const newHeroes = heroes.slice();

// 替换整个元素,原数组不受影响
newHeroes[0] = {name: 'Spider-Man'};
console.log(heroes[0].name); // 输出:Iron Man

// 修改元素属性,原数组跟着变
newHeroes[1].name = 'Cap';
console.log(heroes[1].name); // 输出:Cap

如果想要创建一个完全独立、修改属性也不会影响原数组的副本,那你需要做深拷贝。常见的方法有:

  • 用JSON.parse(JSON.stringify(heroes)):优点是简单,缺点是无法处理函数、Symbol、循环引用这类特殊值
  • 手写递归深拷贝函数:自己遍历每个元素,如果是引用类型就继续递归拷贝
  • 用成熟的工具库(比如Lodash的_.cloneDeep):适合复杂场景

内容的提问来源于stack exchange,提问作者Guilherme Chiara

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.19 09:07:33