Map, Set

Rosevillage·2023년 2월 17일
0

자바스크립트의 자료형 중 하나인 맵에 대해서 정리한다.

Map

언뜻보면 객체와 유사해보이는 자료형으로,
키가 있는 데이터를 저장한다는 점에서 객체와 유사하지만 객체와 달리 키에 다양한 자료형을 허용한다.

MapObject
의도치 않은 key기본적으로 키를 포함하지 않으며,
명시적으로 입력된 내용만 포함한다.
prototype으로 인해 기본 키가 존재해, 주의하지 않으면
설정한 키과 충돌 할 수 있다.
보안사용자가 제공하는 키와 값에 대해서
안전하게 사용가능
사용자가 제공한 키-값 쌍을 공격자가 객체의 프로토타입을
재정의하여 객체 주입 공격을 발생시킬 수 있다.
key 유형모든 타입 가능string, symbol
키 순서삽입 순서대일반적으로 정렬되어 있지만 항상 그런것은 아니다
결과적으로 속성 순서에 의존하지 않는 것이 가장 좋다.
크기 측정iterable이므로 직접 반복 가능수동으로 Object.keys()나 Object.entries()를 통해
반복 가능 항목을 얻을 수 있다.
성능키-값 쌍의 빈번한 추가 및 제거와
관련된 상황에서는 성능이 좀 더 좋다.
키-값 쌍의 빈번한 추가 및 제거에 최적화되지 않아있다.
직렬화 및 parsing기본 지원이 없다.JSON.stringify()를 통한 JSON으로의 직렬화 지원
JSON.parse()를 통한 객체로의 구문분석 기본지원

주요 메서드와 프로퍼티

  • new Map() : 새로운 Map 객체를 생성
  • map.set(key, value) : key를 이용해 value를 저장, Map 객체를 반환
  • map.get(key) : key에 해당하는 값을 반환, 없다면 undefined
  • map.has(key) : key에 해당하는 값이 존재하는지 boolean 값으로 반환
  • map.delete(key) : key에 해당하는 값을 삭제, 성공 여부 boolean 값으로 반환
  • map.clear() : Map 객체의 모든 키-값 쌍을 제거
  • map.size : Map 객체의 키-값 쌍의 개수를 반환

추가적인 메서드들

반복 관련

다음 메서드를 통해 각 요소를 반복해 사용할 수 있다.

  • map.keys() : 각 요소의 키를 모은 iterable 객체를 반환
  • map.values() : 각 요소의 값을 모든 iterable 객체를 반환
  • map.entries() : 요소의 키-값 쌍을 모든 iterable 객체를 반환(for..of 반복문의 기초로 사용됨)
let map = new Map([
  ['a', 100],
  ['b', 200],
  ['c', 50]
]);

// 키(vegetable)를 대상으로 순회.
for (let key of map.keys()) {
  console.log(key); // cucumber, tomatoes, onion
}

// 값(amount)을 대상으로 순회
for (let value of map.values()) {
  console.log(value); // 500, 350, 50
}

// 키-값 쌍을 대상으로 순회
for (let entry of map) { // map.entries()와 동일
  console.log(entry); // cucumber,500 ...
}

변환 관련

다음 메서드들을 통해 Map을 객체로 또는 객체를 Map으로 변환 할 수 있다.

  • Object.entries : for..in 문과 같이 객체 자체와, 가까운 순서의 prototype의 모든 열거가능한 속성 키-값 쌍의 배열을 반환한다.

    각 요소가 키-값 쌍인 배열이나 이터러블 객체를 초기화 용도로 Map에 전달해 새로운 Map을 만들 수 있다.

    // 각 요소가 [키, 값] 쌍인 배열
    let map = new Map([
      ['1',  'str'],
      [1,    'num'],
      [true, 'bool']
    ]);
    
    console.log( map.get('1') ); // str
    
    // 객체
    let obj = {
     name: "John",
     age: 30
    };
    // 둘은 같은 형태를 가지고 있다.
    Object.entries(obj) => [["name", "John"],["age", 30]]
    
    let map = new Map(Object.entries(obj));
    
    console.log( map.get('name') ); // John
  • Object.fromEntries : 키-값 쌍의 목록(iterable 객체)을 객체로 변환

    키-값 쌍의 목록을 객체로 변환할 수 있다.

    //각 요소가 [키, 값] 쌍인 배열
    let prices = Object.fromEntries([
     ['banana', 1],
     ['orange', 2],
     ['meat', 4]
    ]);
    //prices = { banana: 1, orange: 2, meat: 4 }
    
    console.log(prices.orange); // 2
    
    // Map
    let map = new Map();
    map.set('banana', 1);
    map.set('orange', 2);
    map.set('meat', 4);
    
    let obj = Object.fromEntries(map.entries()); // === Object.fromEntries(map)
    //{ banana: 1, orange: 2, meat: 4 }
    
    console.log(obj.orange); // 2

Set

자료형에 관계없이 유일한 값을 저장하는 값 컬렉션이다.

주요 메서드와 프로퍼티

  • new Set(iterable) : iterable 객체를 받으면(대부분 배열) 그 안의 값을 복사해 Set에 넣어준다
  • set.add(value) : 값을 추가, Set 객체를 반환
  • set.delete(value) : 값을 제거, 성공 여부를 boolean 값으로 반환
  • set.has(value) : 값이 존재 여부를 boolean 값으로 반환
  • set.clear() Set 객체의 모든 값을 삭제
  • set.size : Set 객체의 모든 값의 개수를 반환

추가적인 메서드들

반복 관련

  • set.keys() : Set 객체의 모든 값을 포함하는 iterable 객체를 반환
  • set.values() : Set.keys 와 동일 한 작업, Map과의 호환성을 위해 만들어졌다.
  • set.entries() : Set 객체의 가 값을 이용해 만든 [value, value] 배열을 포함하는 iterable 객체를 반환, Map과의 호환성을 위해 만들어졌다.

for..offorEach를 사용해 반복할 수 있다.

let set = new Set(["oranges", "apples", "bananas"]);

for (let value of set) {
  console.log(value);
}

// 둘다 동일하게 동작

set.forEach((value, valueAgain, set) => {
  console.log(value);
});

forEach 가 다른 타입들이 사용할 때와 달리 두 번째 인자가 index가 아닌 첫 번째 인자와 같은 해당 값을 받는데, 이는 Map 과의 호환성을 위해서 이렇게 구현되었다.

마무리

  • Map은 키-값 쌍으로 저장된 반복 가능 컬렉션이다.
  • Set은 중복 없는 유일한 값들이 저장된 반복 가능 컬렉션이다.

Map과 Set이 반복작업을 할 땐, 해당 컬렉션에 요소나 값을 추가한 순서대로 진행된다.

그래서 이 두 객체는 정렬이 되어있지 않다고 할 수 없으나 컬렉션 내 요소나 값을 재 정렬하거나 (배열에서 인덱스를 이용해 요소를 가져오듯이) 숫자를 이용해 특정 요소나 값을 가지고 오는 것은 불가능 하다.


참고 사이트

Javascript.info-코어 자바스크립트-맵과 셋

MDN-Javascript 참고서-Map

MDN-Javascript 참고서-Set

0개의 댓글