ECMAScript
最新提案: "通过复制更改数组",该提案为数组提供了四种新方法:
.toReversed()
.toSorted()
.toSpliced()
.with()
新提供的四种方法是非破坏性的数组方法。
破坏性数组方法
什么是破坏性的语法呐?破坏性语法是指一些数组方法会修改数组本身。
例如 sort
方法,sort
方法的返回值与调用数组指向同一对象,详情参考下面代码:
// Destructively sorting `arr`
const arr = ['c', 'a', 'b'];
const result = arr.sort();
assert.deepEqual(result, ['a', 'b', 'c']);
assert.ok(result === arr); // (A)
assert.deepEqual(arr, ['a', 'b', 'c']);
如果我们想要消除 sort
方法的破坏性,可以先复制数组,然后再更改复制后的数组。
const sorted1 = arr.slice().sort();
const sorted2 = [...arr].sort();
const sorted3 = Array.from(arr).sort();
除了 sort
方法,以下方法也具有破坏性:
reserve
splice
新的非破坏性数组方法
toReversed()
toReversed
方法是与 reverse
方法对应的非破坏性数组方法。
该方法目前为提案阶段,你可以通过 polyfill.toReversed
来使用
if (!Array.prototype.toReversed) {
Array.prototype.toReversed = function () {
return this.slice().reverse();
};
}
.toSorted()
toSorted()
是与 sort()
对应的非破坏性数组方法。
该方法目前为提案阶段,你可以通过 polyfill.toSorted
来使用
if (!Array.prototype.toSorted) {
Array.prototype.toSorted = function (compareFn) {
return this.slice().sort(compareFn);
};
}
toSpliced(start, deleteCount, ...items)
splice
方法的破坏性非常复杂,它的具体机制是这样的:
- 从索引
start
开始,删除deleteCount
数量的元素 - 可以在索引
start
位置插入元素 - 返回被删除的元素
toSpliced()
是与 splice()
对应的非破坏性数组方法。由于它需要返回调用数组的更改版本,因此不允许访问已删除元素。
该方法目前为提案阶段,你可以通过 polyfill.toSpliced
来使用
if (!Array.prototype.toSpliced) {
Array.prototype.toSpliced = function (start, deleteCount, ...items) {
const copy = this.slice();
copy.splice(start, deleteCount, ...items);
return copy;
};
}
with
with
方法没有对应的破坏性方法,它的功能是非破坏性的修改索引 index 对应的元素值(即非破坏的 arr[index]=value
)
该方法目前为提案阶段,你可以通过 polyfill.with
来使用
if (!Array.prototype.with) {
Array.prototype.with = function (index, value) {
const copy = this.slice();
copy[index] = value;
return copy;
};
}
新方法适用于元组
新提议的 Tuple 特性本质上是一个不可变的数组,因此元组具有数组的所有方法(破坏性方法除外),因此后续添加的非破坏性方法元组也是可以使用的。
如果你想了解当前提案的更多讯息,参考 2ality.com/2022/04/cha…