【JS】forEach 可以改变原数组吗?

173 阅读1分钟

本质上,forEach 是将数组的元素值复制一份到新的内存空间中,再进行操作

  1. 对于基本类型,值的复制就是对值本身的复制,故对复制值的操作不会影响原值
let arr = [1, 2, 3, 4, 5]

arr.forEach((v, i, arr) => {
    v *= 2
})

console.log(arr)  // [1, 2, 3, 4, 5]
  1. 对于引用类型,值的复制是对对象地址的复制,故复制值和原值是指向同一个内存空间的
let persons = [
    {
        name: '小明',
        age: 18
    },
    {
        name: '张三',
        age: 16
    }
]

persons.forEach((v, i, arr) => {
    if(v.name === "张三"){
        v.age = 28
    }
})

console.log(persons)  // [{name:'小明', age:18}, {name:'张三', age:28}]

需要注意的是:上面的修改是对同一个内存空间内对象内部数据的修改,并没有改变复制值(地址)的指向

如果是下面这种,直接改变地址指向的修改,也是对原数组产生不了影响的
let persons = [
    {
        name: '小明',
        age: 18
    },
    {
        name: '张三',
        age: 16
    }
]

persons.forEach((v, i, arr) => {
    if(v.name === "张三"){
        v = {
            name: '李四',
            age: '21'
        }
    }
})

console.log(persons)  // [{name:'小明', age:18}, {name:'张三', age:16}]

那么有没有可以直接改变原数组数据的写法呢?有的,直接对原数组进行操作就好啦~

/* 基本类型 */
let arr = [1, 2, 3, 4, 5]

arr.forEach((v, i, arr) => {
    arr[i] *= 2
})

console.log(arr)  // [2, 4, 6, 8, 10]



/* 引用类型 */
let persons = [
    {
        name: '小明',
        age: 18
    },
    {
        name: '张三',
        age: 16
    }
]

persons.forEach((v, i, arr) => {
    if(v.name === "张三"){
        arr[i] = {
            name: '李四',
            age: 30
        }
    }
})

console.log(persons)  // [{name:'小明', age:18}, {name:'李四', age:30}]