通过引用交换对象?

时间:2016-04-30 02:47:00

标签: javascript

我正在寻找使用swap函数交换两个对象,只需参考它们。

典型的用例如下:

function swap(a, b) {
    ...
}

var a = [ { id: 1 }, { id: 2 } ]
swap(a[0], a[0])
console.log(a) // [ { id: 2 }, { id: 1 } ]

var one = { id: 1 }
var two = { id: 2 }
swap(one, two)
console.log(one) // Should be { id: 2 }
console.log(two) // Should be { id: 1 }

(添加了一些用例。swap不应该依赖于任何数组功能。)

这可能吗?我知道javascript的函数是copy-reference source。基本上,swap(a, b)的{​​{1}}和a只是ba[0]的副本,所以我似乎无法将它们交换掉实际上将a[1]的字段复制到a的字段中,反之亦然,这似乎不切实际。

编辑:@timolawl指出ES6的解构,但它似乎不适用于这个用例:

b

jsfiddle

3 个答案:

答案 0 :(得分:3)

使用ES6,您可以使用destructuring

一般情况:

[a, b] = [b, a];

示例:

let one = { id: 1 };
let two = { id: 2 };

document.body.insertAdjacentHTML('beforeend', '<pre>' + JSON.stringify(one, 0, 4) + '</pre>');
document.body.insertAdjacentHTML('beforeend', '<pre>' + JSON.stringify(two, 0, 4) + '</pre>');

[one, two] = [two, one];

document.body.insertAdjacentHTML('beforeend', '<pre>' + JSON.stringify(one, 0, 4) + '</pre>');
document.body.insertAdjacentHTML('beforeend', '<pre>' + JSON.stringify(two, 0, 4) + '</pre>');

答案 1 :(得分:2)

可以重构此功能以实现您想要的功能 - 提供数组和两个索引并根据这些指数进行交换。例如:

function swap(array, a, b) {
    var temp = array[a]; // store a temporary copy of the variable

    // perform the swap
    array[a] = array[b];
    array[b] = temp;
}

请注意,临时副本是必要的,因为设置array[a] = array[b]时数据会被覆盖 - 因此您必须事先存储array[a]的值。

答案 2 :(得分:1)

通过深层复制交换

没有简单的方法。 Object.assign可以提供帮助,但链中的任何属性都只是浅层副本。还有cludgy JSON副本。 var b = JSON.parse(JSON.stringify(a));但是这不处理函数并忽略所有未分配的属性,并且不能处理任何循环数据(这都是常见的)。你可以迭代属性和原型链并使用Object.hasOwnProperty但是你仍然不知道副本应该有多深,如何锻炼继承等等

通常,副本(或交换)需要了解数据的含义和上下文。有些人可能认为它不是Javascript青睐的短暂下降,但是一般的交换或复制功能会打破许多功能编程,数据封装等规则,所有这些都有很好的推理理由。

这个以及更多原因是为什么没有提供方便的深层复制的动作。