iT邦幫忙

2018 iT 邦幫忙鐵人賽
DAY 11
0
Modern Web

重新學習網頁設計系列 第 11

DAY 11. JavaScript Map and Set

DAY 11. JavaScript Map and Set

MapSetes6提供兩種新的數據結構
這個單元將討論他們與Array, Object的差異
以及我們可以在什麼情況使用它們。

Map

Map跟物件非常相近,當我們需要鍵值時常會用到物件
但物件有幾個缺點

  • 物件原型特性,可能使我們對應到不需要的東西
  • 沒有簡單的方法查詢一個物件裡有多找東西
  • 鍵必須是字串或符號,無法將物件設為鍵
  • 物件無法保證特性順序
    Map能夠解決這些缺點,尤其是能夠將物件設為鍵的特性更是好用

Map 建構式

new Map([iterable])
Iterable 是一個陣列或其他iterable物件,該物件的元素皆是鍵/值成對的(例如兩個元素的陣列)
成對的鍵/值會被新增到新的Map。null會被作為undefined

操作範例

const u1 = {name: 'Peter'}
const u2 = {name: 'Sam'}
const u3 = {name: 'Cindy'}

// 建構式賦值
const userRoles = new Map([
  [u1, 'User'], [u2, 'User'], [u3, 'Admin']
])

/*
 | 使用set方法逐一賦值
 */
userRoles.set(u1, 'User')
userRoles.set(u2, 'User')
userRoles.set(u3, 'Admin')

/*
 | 使用set方法鏈接賦值
 */
userRoles.set(u1, 'User')
         .set(u2, 'User')
         .set(u3, 'Admin')

// 以上三種方式都會得到一樣的結果
const userRolesSize = userRoles.size
console.log(userRolesSize) //  3

/*
 | 使用get方法取得鍵值
 */
 console.log(userRoles.get(u1)) // "User"
 
/*
 | 使用has方法確認鍵是否存在
 */
 const u100 = {name: 'Hank'}
 console.log(userRoles.has(u1))   // true
 console.log(userRoles.has(u100)) // false
 console.log(userRoles.get(u100)) // undefined
 
/*
 | 使用has方法確認鍵是否存在
 */
 const u100 = {name: 'Hank'}
 console.log(userRoles.has(u1))   // true
 console.log(userRoles.has(u100)) // false
 console.log(userRoles.get(u100)) // undefined
 
/*
 | 使用keys方法取得map鍵
 */
for(let u of userRoles.keys())
  console.log(u.name)
// "Peter"
// "Sam"
// "Cindy"

/*
 | 使用values方法取得map值
 */
for(let v of userRoles.values())
  console.log(v)
// "User"
// "User"
// "Admin"

/*
 | 使用entries方法取得項目陣列
 */
for(let [u, r] of userRoles.entries())
  console.log(`${u.name} is ${r}`)
//   Peter is User
//   Sam is User
//   Cindy is Admin

/*
 | entries方法是map預設迭代器
 | 因此其實上面例子我們可以省略entries()
 */
for(let [u, r] of userRoles)
  console.log(`${u.name} is ${r}`)
//   Peter is User
//   Sam is User
//   Cindy is Admin

/*
 | 我們可以使用擴張運算子來將map轉為陣列
 */
console.log([...userRoles.keys()])
// [ { name: 'Peter' }, { name: 'Sam' }, { name: 'Cindy' } ]

console.log([...userRoles.values()])
// [ 'User', 'User', 'Admin' ]

console.log([...userRoles])
// [ [ { name: 'Peter' }, 'User' ],
//   [ { name: 'Sam' }, 'User' ],
//   [ { name: 'Cindy' }, 'Admin' ] ]

/*
 | 使用delete方法刪除項目
 */
userRoles.delete(u1)
console.log(userRoles.has(u1))  // false

/*
 | 使用clear方法刪除所有項目
 */
userRoles.clear()
console.log(userRoles.size)  // 0

Set

Set類似Array, 但其中元素的值都會是唯一不重複的
Set甚至可以搭配Array使用,例如將Array的值unique

Set 建構式

new Set([iterable])
Set接受一個可迭代的參數或是null或是不給予
且建構式將回傳一個Set物件實例


const setArr1 = new Set()
console.log(setArr1)
// [object Set] 

const arr = [1, 2, 3, 4, 5, 5, 5]
const setArr2 = new Set(arr)
for (let i of setArr2) { 
   console.log(i)
}
// 1 2 3 4 5

前面我們提到,Set的值將會唯一,但給予的參數不會自轉型別
因此數字5字串5將被視為不同的兩個值。

const set = new Set()

/*
 | add 方法新增元素
 */
set.add(1)
set.add(2)
console.log(set.size)   // 2

/*
 | add 方法也可以使用串接的方式
 */
set.add(5)
   .add('5')
console.log(set.size)   // 4

/*
 | 試著加入相同屬性驗證set不會記錄相同項目
 */
set.add('5')
console.log(set.size)   // 4

/*
 | delete 方法移除set中的元素,返回true/false
 */
console.log(set.delete(1))         // true
console.log(set.delete('apple'))   // false
console.log(set.size)              // 3

還有另外兩個類別稱為WeakMapWeakSet
他們的用途沒那麼的廣泛,有興趣的朋友請自行查閱相關文件。

資料來源: JavaScript學習手冊, MDN


上一篇
DAY 10. JavaScript 類別與物件
下一篇
DAY 12. JavaScript 物件特性設置
系列文
重新學習網頁設計30

尚未有邦友留言

立即登入留言