【Java】Map和Set

Map和Set

  • [两种数据模型:Key 与 Key-Value](#两种数据模型:Key 与 Key-Value)
  • [Map 详解:键值对的映射容器](#Map 详解:键值对的映射容器)
    • [Map 的概念](#Map 的概念)
    • [Map.Entry<K, V> ⭐](#Map.Entry<K, V> ⭐)
    • [Map 常用 API](#Map 常用 API)
    • Map的特点
    • [HashMap vs TreeMap](#HashMap vs TreeMap)
  • [Set 详解:唯一元素的集合](#Set 详解:唯一元素的集合)
    • [Set 的概念](#Set 的概念)
    • [Set 常用 API](#Set 常用 API)
    • [Set 的特点](#Set 的特点)
    • [HashSet vs TreeSet](#HashSet vs TreeSet)

两种数据模型:Key 与 Key-Value

  • 纯 Key 模型 :只存储关键字,用于判断"某个元素是否存在"。典型场景包括:判断单词是否在词典中、检查用户名是否已被注册。

  • Key-Value 模型:不仅存储关键字,还关联一个对应的值。典型场景包括:根据学号查学生信息、统计单词出现次数。

简单来说:Set 对应纯 Key 模型,Map 对应 Key-Value 模型 。在 Java 集合框架中,两者都是接口,需要通过具体实现类来使用 :

  • Map 实现类:HashMap、TreeMap(均实现 Map 接口)
  • Set 实现类:HashSet、TreeSet(均实现 Set 接口)

Map 详解:键值对的映射容器

Map 的概念

在深入 HashMap 和 TreeMap 之前, 需要先明确 Map 接口的核心定义与约束 :

  • Map 是一个接口类,它没有继承自 Collection 接口,这与 List、Set 不同。
  • Map 中存储的是 <K, V> 结构的键值对,并且 Key 一定是唯一的,不能重复 。当使用 put 方法放入相同的 key 时,新的 value 会覆盖旧的 value。

Map.Entry<K, V> ⭐

Map.Entry<K, V> 是 Map 内部实现的用来存放 <key, value> 键值对映射关系的内部类 。当遍历 Map 时,拿到的就是一个个 Entry 对象。

该内部类主要提供了以下方法:

方法 解释
K getKey() 返回 entry 中的 key
V getValue() 返回 entry 中的 value
V setValue(V value) 将键值对中的 value 替换为指定 value

注意 :Map.Entry<K, V> 并没有提供设置 Key 的方法。这意味着 Map 中键值对的 Key 不能直接修改,如果要修改 Key,只能先将该 key 对应的映射删除,然后再插入新的 key-value 对。

Map 常用 API

以下是 Map 接口中最核心的方法,无论使用 HashMap 还是 TreeMap,这些 API 都是通用的:

方法 解释
V get(Object key) 返回 key 对应的 value,若 key 不存在则返回 null
V getOrDefault(Object key, V defaultValue) 返回 key 对应的 value,若 key 不存在则返回默认值 defaultValue
V put(K key, V value) 设置 key 对应的 value,若 key 已存在则覆盖并返回旧值
V remove(Object key) 删除 key 对应的映射关系,返回被删除的 value
Set<K> keySet() 返回所有 key 的不重复集合(因为 key 唯一)
Collection<V> values() 返回所有 value 的可重复集合(value 可能重复)
Set<Map.Entry<K, V>> entrySet() 返回所有的 key-value 映射关系
boolean containsKey(Object key) 判断是否包含指定的 key
boolean containsValue(Object value) 判断是否包含指定的 value

Map的特点

  • Map 不能直接实例化:Map 是一个接口,必须通过其实现类(如 TreeMap 或 HashMap)来实例化对象。

  • Map下的类不能使用迭代器进行遍历。

  • Key 唯一,Value 可重复:这是 Map 最核心的特性。

  • 关于 null 值的支持差异 :

    • TreeMap :插入键值对时,Key 不能为空 (会抛出 NullPointerException),Value 可以为空。
    • HashMap :Key 和 Value 都可以为空。
  • Key 的分离与访问:Map 中的 Key 可以全部分离出来,存储到 Set 中进行访问(因为 Key 不能重复,正好符合 Set 的特性)。

  • Value 的分离与访问:Map 中的 value 可以全部分离出来,存储在 Collection 的任何一个子集合中(因为 value 可能有重复)。

  • Key 不可直接修改:Map 中键值对的 Key 不能直接修改,value 可以修改。如果要修改 Key,只能先将该 key 删除,然后再重新插入新的键值对。

HashMap vs TreeMap

特性 HashMap TreeMap
底层结构 哈希表(数组+链表+红黑树) 红黑树
时间复杂度 O(1) O(log n)
元素顺序 无序 按键的自然顺序或比较器排序
null 支持 key 和 value 均可为 null key 不能为 null,value 可以为 null
比较要求 自定义对象需重写 hashCode() 和 equals() key 必须实现 Comparable 或传入 Comparator
  • 不关心顺序、追求极致性能 → 选 HashMap
  • 需要按键有序遍历 → 选 TreeMap

从源码深入理解HashMap和TreeMap

Set 详解:唯一元素的集合

Set 的概念

在深入 HashSet 和 TreeSet 之前,需要先明确 Set 接口的核心定义与约束:

  • Set 是继承自 Collection 的一个接口类,这意味着它拥有 Collection 的所有方法,同时有自己的特性约束。
  • Set 的核心特征是元素不可重复 ,向 Set 中添加已存在的元素会被直接忽略 。

Set 常用 API

以下是 Set 接口中最核心的方法,无论使用 HashSet 还是 TreeSet,这些 API 都是通用的:

方法 解释
boolean add(E e) 添加元素,但重复元素不会被添加成功(返回 false)
void clear() 清空集合中的所有元素
boolean contains(Object o) 判断元素 o 是否在集合中
Iterator<E> iterator() 返回迭代器,用于遍历集合
boolean remove(Object o) 删除集合中的元素 o,删除成功返回 true
int size() 返回 Set 中元素的个数
boolean isEmpty() 检测 Set 是否为空,空返回 true,否则返回 false
Object[] toArray() 将 Set 中的元素转换为数组返回
boolean containsAll(Collection<?> c) 判断集合 c 中的元素是否在 Set 中全部存在
boolean addAll(Collection<? extends E> c) 将集合 c 中的元素添加到 Set 中,可以达到去重的效果

Set 的特点

  • Set 中只存储了 Key,并且要求 Key 一定要唯一,不能重复
  • Set 最大的功能就是对集合中的元素进行去重
  • Set 中的 Key 不能修改,如果要修改,只能先将原来的删除掉,然后再重新插入

HashSet vs TreeSet

特性 HashSet TreeSet
底层结构 HashMap(只用 key,value 为固定常量) TreeMap(只用 key)
时间复杂度 O(1) O(log n)
元素顺序 无序 有序(自然顺序或比较器)
null 支持 允许一个 null 元素 不允许 null(会抛 NullPointerException)
比较要求 需重写 hashCode() 和 equals() 元素必须实现 Comparable 或传入 Comparator
相关推荐
wuminyu5 小时前
JVM规范学习总结:解释器与JIT编译器如何处理JVM字节码
java·linux·c语言·jvm·c++
txxzjmzlh5 小时前
SpringBoot 配置⽂件
java·spring boot·spring
小徐不徐说5 小时前
序列化与反序列化:把 C++ 对象可靠地保存下来
开发语言·数据库·c++·php
ragnwang5 小时前
Notes: Python pybind11 import C++ module
开发语言·c++·python
Wang's Blog5 小时前
Java 项目实战: 交友项目 - 搜索附近的功能概述和分析
java·开发语言·交友
骑着蜗牛撵大象3276 小时前
大模型 Agent 的沙箱护栏:gVisor 隔离、出口白名单与审计闭环
java·开发语言·jvm·安全·agent沙箱·gvisor·microvm
独泪了无痕6 小时前
Hutool之LocalDateTimeUtil:让时间间隔操作如虎添翼
java
Dxy12393102167 小时前
JS DES 加密详解
开发语言·javascript·arcgis
充值内卷7 小时前
我给桌面加了个鱼缸:C++ 写后端,WebView2 里养一座 Three.js 小岛
开发语言·javascript·c++
云和数据.ChenGuang7 小时前
深入解析 Python 的 dir():从用法到 CPython 源码实现
开发语言·人工智能·python·langchain