1. Map 이해하기
1.1 Map 이란?
Map 객체는 키-값 쌍을 저장할 수 있는 구조입니다. 여기서 키는 어떤 타입도 될 수 있습니다. Map은 각 키와 값의 쌍을 유지하며, 객체보다 유연하고 강력한 기능을 제공합니다.
let m = new Map();
console.log(m); // Map(0) {}
Map 문법은 ES6에 추가된 문법입니다. 다만 객체와 그 용도가 비슷하기 때문에 그동안 객체를 사용해왔던 개발자들은 Map을 잘 모르거나 사용하지 않는 경우가 많습니다. 하지만 Map은 객체보다 더 많은 기능을 제공하며, 객체보다 더 효율적으로 데이터를 다룰 수 있습니다. 이제는 충분히 성숙된 문법입니다. 안심하고 사용하셔도 됩니다.
"JavaScript Set" | Can I use... Support tables for HTML5, CSS3, etc
"Map()" | Can I use... Support tables for HTML5, CSS3, etc
위니북스에서 Map과 Set 전체가 출력되지 않습니다.
위니북스는 바로 뒤 챕터에서 배울 JSON.stringify를 사용하여 객체를 출력하기 때문에 Map과 Set은 출력되지 않습니다. 따라서 Map과 Set을 사용할 때는 위니북스가 아닌 콘솔 환경에서 테스트하세요.
다만 위니북스에서 쉽게 확인할 수 있도록 ...(스프레드 문법)을 사용하여 Map과 Set을 배열로 변환하여 출력하도록 해놓았습니다.
이렇게 굳이 위니북스에서 실행되게 해놓은 이유는 결국 실무에서도 비슷한 작업을 여러분이 해야하기 때문입니다.
1.2 Map에 값 추가하기
Map에 값을 추가할 때는 set 메서드를 사용합니다. 객체는 문자열만 키로 사용할 수 있지만, Map은 어떤 타입도 키로 사용할 수 있습니다. 아래 코드를 실행시켜 출력되는 값을 확인해보고 여러 타입의 값을 키로 활용해보세요.
let m = new Map();
m.set('하나', '1');
m.set(1, '하나');
m.set(true, 1);
m.set(false, 0);
m = [...m] // 위니북스에서만 이렇게 사용
console.log(m);
원래 map의 형태는 아래와 같이 출력됩니다. 콘솔에서 확인해보세요.
Map(4) {
"하나" => "1",
1 => "하나",
true => 1,
false => 0
}
Map(4) {
"하나" => "1",
1 => "하나",
true => 1,
false => 0
}
1.3 Map에서 값 가져오기
Map에서 값을 가져올 때는 get 메서드를 사용합니다.
let m = new Map();
m.set('하나', '1');
m.set(true, 1);
console.log(m.get('하나')); // '1'
console.log(m.get(true)); // 1
1.4 Map에 값이 있는지 확인하기
Map에 특정 키가 있는지 확인할 때는 has 메서드를 사용합니다. 객체에서 사용했던 in연산자와 같은 역할을 하며 만약 map에서 in연산자를 사용하면 의도한 것처럼 동작하지 않으니 주의해주세요.
let m = new Map();
m.set('하나', '1');
console.log(m.has('하나')); // true
console.log(m.has(2)); // false
1.5 Map에서 값 제거하기
Map에서 값을 제거할 때는 delete 메서드를 사용합니다.
let m = new Map();
m.set('하나', '1');
console.log(m.delete('하나')); // true
console.log(m.has('하나')); // false
1.6 Map의 크기 확인하기
객체에서는 크기를 확인할 수 있는 속성이 없었으나 Map에서는 크기를 확인할 때는 size 속성을 사용할 수 있습니다.
let m = new Map();
m.set('하나', '1');
m.set(1, '하나');
console.log(m.size); // 2
1.7 Map의 모든 데이터 삭제하기
Map의 모든 데이터를 삭제할 때는 clear 메서드를 사용합니다.
let m = new Map();
m.set('하나', '1');
m.set(1, '하나');
m.clear();
console.log(m.size); // 0
1.8 Map 순회하기
Map은 다양한 방법으로 순회할 수 있습니다. for...of 반복문을 사용하면 키와 값을 쉽게 접근할 수 있습니다.
const data = new Map().set('name', 'licat').set('age', 10).set('height', 180);
for (const value of data) {
console.log(value[0]);
console.log(value[1]);
}
for (const [key, value] of data) {
console.log(key);
console.log(value);
}
1.9 Map의 키와 값에 접근하기
객체는 키와 값에 접근할 때 Object.keys, Object.values 메서드를 사용했지만, Map의 키와 값에 각각 접근할 때는 keys와 values 메서드를 사용합니다.
const data = new Map().set('name', 'hojun').set('age', 10).set('height', 180);
console.log([...data.keys()]); // ["name", "age", "height"]
console.log([...data.values()]); // ["hojun", 10, 180]
1.10 배열과 Map의 변환
배열을 Map으로 변환하거나, 그 반대로 변환할 수 있습니다.
// 배열을 Map으로 변환
let temp = new Map([
[1, 10],
[2, 20],
[3, 30],
[4, 40],
]);
temp = [...temp]; // 위니북스에서만 이렇게 사용
console.log(temp); // Map(4) {1 => 10, 2 => 20, 3 => 30, 4 => 40}
// 객체를 Map으로 변환
let temp2 = new Map(Object.entries({ one: 1, two: 2 }));
temp2 = [...temp2]; // 위니북스에서만 이렇게 사용
console.log(temp2); // Map(2) {"one" => 1, "two" => 2}
// Map을 객체로 변환
const temp3 = Object.fromEntries(temp2);
console.log(temp3); // { one: 1, two: 2 }
1.11 Map과 Object의 차이
Map 객체와 Object는 모두 키-값 쌍을 저장하지만, 몇 가지 중요한 차이점이 있습니다.
// Object의 키는 문자열과 심볼 타입만 가능하지만, Map의 키는 모든 값을 가질 수 있습니다.
let objMap = new Map();
objMap.set('one', 1);
objMap.set(2, 'two');
objMap.set(true, 3);
objMap = [...objMap]; // 위니북스에서만 이렇게 사용
console.log(objMap); // Map(3) {"one" => 1, 2 => "two", true => 3}
// Object는 크기를 수동으로 계산해야 하지만, Map은 size 속성을 통해 쉽게 크기를 확인할 수 있습니다.
let obj = { hi: 1, hi2: 2, hi3: 3, hi4: 4 };
console.log(Object.keys(obj).length); // 4
console.log(objMap.size); // 3
2. Set 이해하기
2.1 Set 이란?
Set 객체는 중복되지 않는 값들의 집합을 저장할 수 있는 구조입니다. Set은 각 값을 유일하게 유지하며, 중복된 값을 허용하지 않습니다. Set은 Map과 같이 ES6에 추가된 문법입니다. 역시나 충분히 성숙된 문법이니 안심하고 사용하셔도 됩니다.
let s = new Set();
console.log(s); // Set(0) {}
2.2 Set에 값 추가하기
Set에 값을 추가할 때는 add 메서드를 사용합니다.
let s = new Set();
s.add('apple');
s.add('banana');
s.add('orange');
s = [...s]; // 위니북스에서만 이렇게 사용
console.log(s); // Set(3) {"apple", "banana", "orange"}
중복을 허용하는지 테스트 해보도록 하겠습니다.
let s = new Set();
s.add(1);
s.add(1);
s.add(2);
s.add(2);
s.add(3);
s = [...s]; // 위니북스에서만 이렇게 사용
console.log(s); // Set(3) {1, 2, 3}
아래처럼 문자열을 바로 Set으로 변경하여 중복을 허락하는지 테스트 해볼 수도 있습니다.
let s = new Set('abcdeeeeeeeee');
s = [...s]; // 위니북스에서만 이렇게 사용
console.log(s);
console.log(s.size);
2.3 Set에서 값 확인하기
Set에 특정 값이 있는지 확인할 때는 has 메서드를 사용합니다.
let s = new Set(['apple', 'banana', 'orange']);
console.log(s.has('apple')); // true
console.log(s.has('grape')); // false
2.4 Set에서 값 제거하기
Set에서 값을 제거할 때는 delete 메서드를 사용합니다.
let s = new Set(['apple', 'banana', 'orange']);
console.log(s.delete('banana')); // true
console.log(s.has('banana')); // false
2.5 Set의 크기 확인하기
Set의 크기를 확인할 때는 size 속성을 사용합니다.
let s = new Set(['apple', 'banana', 'orange']);
console.log(s.size); // 3
2.6 Set의 모든 데이터 삭제하기
Set의 모든 데이터를 삭제할 때는 clear 메서드를 사용합니다.
let s = new Set(['apple', 'banana', 'orange']);
s.clear();
console.log(s.size); // 0
2.7 Set 순회하기
Set은 다양한 방법으로 순회할 수 있습니다. for...of 반복문을 사용하면 값을 쉽게 접근할 수 있습니다.
let s = new Set(['apple', 'banana', 'orange']);
for (let value of s) {
console.log(value);
}
2.8 배열과 Set의 변환
배열을 Set으로 변환하거나, 그 반대로 변환할 수 있습니다.
// 배열을 Set으로 변환
let arr = ['apple', 'banana', 'orange', 'banana'];
let s = new Set(arr);
console.log(s); // Set(3) {"apple", "banana", "orange"}
// Set을 배열로 변환
let newArr = [...s];
console.log(newArr); // ["apple", "banana", "orange"]
2.9 Set을 이용한 중복 제거
Set을 사용하면 배열의 중복된 값을 쉽게 제거할 수 있습니다.
let arr = ['apple', 'banana', 'orange', 'banana'];
let uniqueArr = [...new Set(arr)];
console.log(uniqueArr); // ["apple", "banana", "orange"]
2.10 Set의 교집합, 합집합, 차집합
Set을 사용하여 교집합, 합집합, 차집합을 구할 수 있습니다.
let setA = new Set(['apple', 'banana', 'orange']);
let setB = new Set(['banana', 'kiwi', 'orange']);
// 교집합
let intersection = new Set([...setA].filter(x => setB.has(x)));
intersection = [...intersection]; // 위니북스에서만 이렇게 사용
console.log(intersection); // Set(2) {"banana", "orange"}
// 합집합
let union = new Set([...setA, ...setB]);
union = [...union]; // 위니북스에서만 이렇게 사용
console.log(union); // Set(4) {"apple", "banana", "orange", "kiwi"}
// 차집합
let difference = new Set([...setA].filter(x => !setB.has(x)));
difference = [...difference]; // 위니북스에서만 이렇게 사용
console.log(difference); // Set(1) {"apple"}