0
点赞
收藏
分享

微信扫一扫

[JS] Map中keys的有序性

1. 背景

mdn: Map是ES6中的内置全局对象,其中保存了多个键值对映射关系。
它的key 和value 都可以是js中的任意对象。例如,

const m = new Map;

const objectKey1 = {};
const objectKey2 = {};
const stringKey3 = '';
const numberKey4 = Infinity;

m.set(objectKey1, 1);
m.set(objectKey2, 2);
m.set(stringKey3, 3);
m.set(numberKey4, 4);

const iter = m.keys();
console.assert(iter.next().value === objectKey1);
console.assert(iter.next().value === objectKey2);
console.assert(iter.next().value === stringKey3);
console.assert(iter.next().value === numberKey4);

这里我们看到,m.keys()是按key的插入顺序返回的。
mdn中的解释如下,

但是这种顺序性到底是否与实现相关呢,还是一种规范呢。
下面我们查阅ECMAScript规范来确认下。

2. Map

规范中Map相关的章节中,并没有提及顺序性。
只是对实现有这样的限制,

2.1 Map.prototype.keys

我们直接看Map.prototype.keys的操作语义,

其中,CreateMapIterator会返回一个iterator,

2.2 %MapIteratorPrototype%

%MapIteratorPrototype%是Map返回的所有iterator的原型对象。

我们来看它的next方法是怎样定义的,

其中第9步是关键,entries是一个List,它的值是m.[[MapData]]
其中List是一个规范内置类型(Specification Types)。

因此,List是有顺序的。

2.3 [[MapData]]

那么m.[[MapData]]是怎么来的呢?它是在Map的构造函数中初始化的。

第3步,构造函数初始化map.[[MapData]]为一个空List。

2.4 Map.prototype.set

再看Map.prototype.set,

看第8步,可见Map中的key在逻辑上是顺序存储的。


参考

mdn: Map

举报

相关推荐

0 条评论