Java의 Map은 키와 값을 쌍으로 저장하며 중복 키를 허용하지 않는 컬렉션 프레임워크의 중요한 인터페이스입니다. 여러 구현체가 존재하여 각각의 특성과 장점에 따라 다양한 상황에서 사용할 수 있습니다. 이번 글에서는 Java에서 제공하는 주요 Map 인터페이스와 구현체인 HashMap, LinkedHashMap, TreeMap, Hashtable의 특징과 사용법을 다루겠습니다.

Map 인터페이스의 구조와 메서드
Java Map 인터페이스는 Java Collections Framework의 중요한 요소로, 키-값 쌍으로 데이터를 저장하는 역할을 합니다. Map 인터페이스는 아래와 같은 주요 메서드를 제공합니다:
- put(K key, V value): 키-값 쌍을 Map에 추가합니다. 기존 키가 존재하면 기존 값을 대체합니다.
- get(Object key): 주어진 키에 해당하는 값을 반환합니다.
- remove(Object key): 주어진 키와 관련된 값을 제거합니다.
- containsKey(Object key): 특정 키가 존재하는지 확인합니다.
- containsValue(Object value): 특정 값이 존재하는지 확인합니다.
- size(): Map에 포함된 키-값 쌍의 개수를 반환합니다.
- clear(): 모든 키-값 쌍을 삭제하여 Map을 초기화합니다.
- keySet(): Map에 저장된 모든 키를 Set으로 반환합니다.
- values(): Map에 저장된 모든 값을 Collection으로 반환합니다.
- entrySet(): Map의 모든 키-값 쌍을 Set 형태로 반환합니다.
Map 인터페이스 예제
import java.util.HashMap;
import java.util.Map;
public class MapExample {
public static void main(String[] args) {
Map<String, Integer> map = new HashMap<>();
map.put("Apple", 10);
map.put("Banana", 20);
map.put("Cherry", 30);
System.out.println("Value for 'Apple': " + map.get("Apple"));
System.out.println("Map contains key 'Banana': " + map.containsKey("Banana"));
System.out.println("Map contains value 30: " + map.containsValue(30));
System.out.println("Map Size: " + map.size());
map.remove("Banana");
System.out.println("Map after removing 'Banana': " + map);
}
}
HashMap: 기본 Map 구현체
HashMap은 가장 일반적인 Map 구현체로, null 값과 null 키를 허용하며 동기화가 되지 않습니다. 내부적으로 해싱 기법을 사용하여 데이터를 저장하므로, 데이터를 순서 없이 빠르게 저장하고 검색하는 데 적합합니다. 다만, 순서가 중요하지 않은 경우에만 사용하는 것이 좋습니다.
HashMap 예제
import java.util.HashMap;
import java.util.Map;
public class HashMapExample {
public static void main(String[] args) {
Map<String, String> capitals = new HashMap<>();
capitals.put("USA", "Washington, D.C.");
capitals.put("France", "Paris");
capitals.put("Japan", "Tokyo");
capitals.put(null, "No Capital");
System.out.println("Capital of USA: " + capitals.get("USA"));
System.out.println("Capital of France: " + capitals.get("France"));
System.out.println("Capital of Japan: " + capitals.get("Japan"));
System.out.println("Null key value: " + capitals.get(null));
}
}
LinkedHashMap: 순서가 유지되는 Map
LinkedHashMap은 입력된 순서 또는 접근된 순서를 유지합니다. null 값과 null 키를 허용하며, HashMap보다 약간 느리지만 순서가 중요한 경우 유용합니다. 예를 들어 캐시와 같은 데이터 구조에 적합합니다.
LinkedHashMap 예제
import java.util.LinkedHashMap;
import java.util.Map;
public class LinkedHashMapExample {
public static void main(String[] args) {
Map<String, Integer> orderMap = new LinkedHashMap<>();
orderMap.put("First", 1);
orderMap.put("Second", 2);
orderMap.put("Third", 3);
System.out.println("Order maintained in LinkedHashMap:");
orderMap.forEach((key, value) -> System.out.println(key + ": " + value));
}
}
TreeMap: 정렬된 Map
TreeMap은 키를 자동으로 정렬하며 null 키를 허용하지 않습니다. 내부적으로 레드-블랙 트리 구조를 사용하므로, 데이터를 정렬된 상태로 유지해야 하는 경우 유용합니다. 일반적으로 범위 검색, 정렬이 필요할 때 TreeMap을 사용합니다.
TreeMap 예제
import java.util.Map;
import java.util.TreeMap;
public class TreeMapExample {
public static void main(String[] args) {
Map<String, Integer> sortedMap = new TreeMap<>();
sortedMap.put("Banana", 2);
sortedMap.put("Apple", 1);
sortedMap.put("Cherry", 3);
System.out.println("TreeMap sorted by keys:");
sortedMap.forEach((key, value) -> System.out.println(key + ": " + value));
}
}
Hashtable: 동기화된 Map
Hashtable은 동기화된 Map으로, 여러 스레드에서 동시에 안전하게 사용할 수 있습니다. 그러나 null 키와 null 값을 허용하지 않습니다. 예전 버전의 Map으로 현재는 주로 멀티스레드 환경에서 ConcurrentHashMap을 사용하는 것이 더 권장됩니다.
Hashtable 예제
import java.util.Hashtable;
import java.util.Map;
public class HashtableExample {
public static void main(String[] args) {
Map<String, String> countryMap = new Hashtable<>();
countryMap.put("India", "New Delhi");
countryMap.put("Australia", "Canberra");
countryMap.put("Canada", "Ottawa");
System.out.println("Hashtable example:");
countryMap.forEach((key, value) -> System.out.println(key + ": " + value));
}
}
각 구현체의 특성과 선택 기준
- HashMap: 순서가 중요하지 않고 빠른 조회가 필요한 경우 사용합니다. null 키와 null 값을 허용하며, 동기화가 필요하지 않은 환경에 적합합니다.
- LinkedHashMap: 입력된 순서 또는 접근된 순서 유지가 필요할 때 사용합니다. 예를 들어, LRU 캐시와 같이 순서가 중요한 경우 유용합니다.
- TreeMap: 자동으로 정렬된 상태로 데이터를 저장해야 하는 경우 사용합니다. 주로 범위 검색이 필요하거나 정렬된 데이터를 다룰 때 적합합니다.
- Hashtable: 동기화가 필요한 환경에서 null을 허용하지 않는 Map이 필요할 때 사용합니다. 다만, 성능과 편의성 면에서 ConcurrentHashMap이 권장됩니다.
'JAVA' 카테고리의 다른 글
| [JAVA] Map Java8 이상의 기능과 메서드 (0) | 2024.11.05 |
|---|---|
| [JAVA] Map 반복문과 순회 방법 (0) | 2024.11.05 |
| [JAVA] Map 메서드 활용 (0) | 2024.11.05 |
| [JAVA] Map 기본 사용법 (0) | 2024.11.02 |
| [JAVA] Map 개요 (0) | 2024.11.02 |
| [JAVA] Lombok 성능 최적화와 메모리 관리 (0) | 2024.11.02 |
| [JAVA] Lombok 커스텀 애너테이션(어노테이션) 생성 및 활용 (0) | 2024.10.31 |
| [JAVA] Lombok 조건부 애너테이션, 어노테이션 (0) | 2024.10.31 |