We read every piece of feedback, and take your input very seriously.
To see all available qualifiers, see our documentation.
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
如果要用一句来描述,我们可以说 Set是一种叫做集合的数据结构,Map是一种叫做字典的数据结构
那什么是集合?什么又是字典呢?
集合,是由一堆无序的、相关联的,且不重复的内存结构【数学中称为元素】组成的组合
字典(dictionary)是一些元素的集合。每个元素有一个称作key 的域,不同元素的key 各不相同
那么集合和字典又有什么区别呢?
大多数主流编程语言都有多种内置的数据集合。例如Python拥有列表(list)、元组(tuple)和字典(dictionary),Java有列表(list)、集合(set)、队列(queue)
Python
list
tuple
dictionary
set
queue
然而 JavaScript 直到ES6的发布之前,只拥有数组(array)和对象(object)这两个内建的数据集合
JavaScript
ES6
array
object
在 ES6 之前,我们通常使用内置的 Object 模拟Map
Object
但是这样模拟出来的map会有一些缺陷,如下:
map
String
Symbol
定义: Set 对象允许你存储任何类型的唯一值,无论是原始值或者是对象引用,Set对象是值的集合,你可以按照插入的顺序迭代它的元素。 Set中的元素只会出现一次,即 Set 中的元素是唯一的
Set
Set本身是一个构造函数,用来生成 Set 数据结构
new Set([iterable])
const set = new Set([1,2,1,2]) console.log(set) // {1,2}
上面代码可以看出 Set 是可以去除数组中的重复元素
属性
console.log(new Set([1,2,1,2]).size) // 2
操作方法
let set = new Set() set.add(1) set.add(2) set.add(2) set.add(3) console.log(set) // {1,2,3} set.has(2) // true set.delete(2) set.has(2) // false set.clear()
遍历方法
let set = new Set([1,2,3,4]) // 由于set只有键值,没有键名,所以keys() values()行为完全一致 console.log(Array.from(set.keys())) // [1,2,3,4] console.log(Array.from(set.values())) // [1,2,3,4] console.log(Array.from(set.entries())) // [[1,1],[2,2],[3,3],[4,4]] set.forEach((item) => { console.log(item)}) // 1,2,3,4
因为 Set 结构的值是唯一的,我们可以很轻松的实现以下
// 数组去重 let arr = [1, 1, 2, 3]; let unique = [... new Set(arr)]; let a = new Set([1, 2, 3]); let b = new Set([4, 3, 2]); // 并集 let union = [...new Set([...a, ...b])]; // [1,2,3,4] // 交集 let intersect = [...new Set([...a].filter(x => b.has(x)))]; [2,3] // 差集 let difference = Array.from(new Set([...a].filter(x => !b.has(x)))); [1]
WeakSet 对象是一些对象值的集合, 并且其中的每个对象值都只能出现一次。在WeakSet的集合中是唯一的
WeakSet 的出现主要解决弱引用对象存储的场景, 其结构与Set类似
WeakSet
与Set的区别
WeakSet 的属性跟操作方法与 Set 一致,不同的是 WeakSet 没有遍历方法,因为其成员都是弱引用,弱引用随时都会消失,遍历机制无法保证成员的存在
上面一直有提到弱引用,那弱引用到底是指什么呢?
弱引用是指不能确保其引用的对象不会被垃圾回收器回收的引用,换句话说就是可能在任意时间被回收
Map 对象保存键值对,并且能够记住键的原始插入顺序。任何值(对象或者原始值) 都可以作为一个键或一个值。一个Map对象在迭代时会根据对象中元素的插入顺序来进行 — 一个 for...of 循环在每次迭代后会返回一个形式为[key,value]的数组
new Map([iterable]) Iterable 可以是一个数组或者其他 iterable 对象,其元素为键值对(两个元素的数组,例如: [[ 1, 'one' ],[ 2, 'two' ]])。 每个键值对都会添加到新的 Map
new Map([iterable])
Iterable
iterable
Map
let map = new Map() map.set('name', 'vuejs.cn'); console.log(map.get('name'))
基本跟 Set 类似,同样具有如下方法 属性
let map = new Map() map.set('name', 'vuejs.cn'); console.log(map.size) // 1 console.log(new Map([['name','vue3js.cn'], ['age','18']]).size) // 2
let map = new Map() map.set('name','vue3js.cn') map.set('age','18') console.log(map) // Map {"name" => "vuejs.cn", "age" => "18"} map.get('name') // vue3js.cn map.has('name') // true map.delete('name') map.has(name) // false map.clear() // Map {}
let map = new Map() map.set('name','vue3js.cn') map.set('age','18') console.log([...map.keys()]) // ["name", "age"] console.log([...map.values()]) // ["vue3js.cn", "18"] console.log([...map.entries()]) // [['name','vue3js.cn'], ['age','18']] // name vuejs.cn // age 18 map.forEach((value, key) => { console.log(key, value)})
Map 会保留所有元素的顺序, 是在基于可迭代的基础上构建的,如果考虑到元素迭代或顺序保留或键值类型丰富的情况下都可以使用,下面摘抄自 vue3 源码中依赖收集的核心实现
vue3
let depsMap = targetMap.get(target) if (!depsMap) { targetMap.set(target, (depsMap = new Map())) } let dep = depsMap.get(key) if (!dep) { depsMap.set(key, (dep = new Set())) } if (!dep.has(activeEffect)) { dep.add(activeEffect) activeEffect.deps.push(dep) ... }
WeakMap 对象是一组键/值对的集合,其中的键是弱引用的。其键必须是对象,而值可以是任意的
与Map的区别
WeakMap 的属性跟操作方法与 Map 一致,同 WeakSet 一样,因为是弱引用,所以 WeakSet 也没有遍历方法
WeakMap
Array
// 解构 const map = new Map([[1, 1], [2, 2], [3, 3]]) console.log([...map]) // [[1, 1], [2, 2], [3, 3]] // Array.from() const map = new Map([[1, 1], [2, 2], [3, 3]]) console.log(Array.from(map)) // [[1, 1], [2, 2], [3, 3]]
const map = new Map([[1, 1], [2, 2], [3, 3]]) console.log(map) // Map {1 => 1, 2 => 2, 3 => 3}
// 非字符串键名会被转换为字符串 function mapToObj(map) { let obj = Object.create(null) for (let [key, value] of map) { obj[key] = value } return obj } const map = new Map().set('name', 'vue3js.cn').set('age', '18') mapToObj(map) // {name: "vue3js.cn", age: "18"}
let obj = {"a":1, "b":2}; let map = new Map(Object.entries(obj))
The text was updated successfully, but these errors were encountered:
No branches or pull requests
如果要用一句来描述,我们可以说
Set是一种叫做集合的数据结构,Map是一种叫做字典的数据结构
那什么是集合?什么又是字典呢?
那么集合和字典又有什么区别呢?
背景
大多数主流编程语言都有多种内置的数据集合。例如
Python
拥有列表(list
)、元组(tuple
)和字典(dictionary
),Java有列表(list
)、集合(set
)、队列(queue
)然而
JavaScript
直到ES6
的发布之前,只拥有数组(array
)和对象(object
)这两个内建的数据集合在
ES6
之前,我们通常使用内置的Object
模拟Map但是这样模拟出来的
map
会有一些缺陷,如下:Object
的属性键是String
或Symbol
,这限制了它们作为不同数据类型的键/值对集合的能力Object
不是设计来作为一种数据集合,因此没有直接有效的方法来确定对象具有多少属性Set
Set
本身是一个构造函数,用来生成Set
数据结构基本使用
new Set([iterable])
接收一个数组(或者具有 iterable 接口的其他数据结构), 返回一个新的Set
对象上面代码可以看出
Set
是可以去除数组中的重复元素属性及方法
属性
操作方法
遍历方法
应用场景
因为
Set
结构的值是唯一的,我们可以很轻松的实现以下WeakSet
WeakSet
的出现主要解决弱引用对象存储的场景, 其结构与Set
类似与
Set
的区别WeakSet
的属性跟操作方法与Set
一致,不同的是WeakSet
没有遍历方法,因为其成员都是弱引用,弱引用随时都会消失,遍历机制无法保证成员的存在上面一直有提到弱引用,那弱引用到底是指什么呢?
Map
基本使用
new Map([iterable])
Iterable
可以是一个数组或者其他iterable
对象,其元素为键值对(两个元素的数组,例如: [[ 1, 'one' ],[ 2, 'two' ]])。 每个键值对都会添加到新的Map
属性及方法
基本跟
Set
类似,同样具有如下方法属性
操作方法
遍历方法
应用场景
Map
会保留所有元素的顺序, 是在基于可迭代的基础上构建的,如果考虑到元素迭代或顺序保留或键值类型丰富的情况下都可以使用,下面摘抄自vue3
源码中依赖收集的核心实现WeakMap
与
Map
的区别WeakMap
的属性跟操作方法与Map
一致,同WeakSet
一样,因为是弱引用,所以WeakSet
也没有遍历方法类型的转换
Map
转为Array
Array
转为Map
Map
转为Object
Object
转为Map
总结
参考
The text was updated successfully, but these errors were encountered: