Java EnumMap 类
提示
- 特定于枚举的映射:
EnumMap
是 Java 集合框架的一部分,专门用于枚举类型的键,提供高效的映射功能。 - 创建和使用 EnumMap:创建
EnumMap
需要指定枚举类型作为键,可使用各种方法像put()
和putAll()
来添加条目。 - 访问和修改元素:
EnumMap
提供方法如get()
,remove()
,replace()
以及entrySet()
,keySet()
,values()
等,用于访问、修改和枚举映射中的元素。
Java 集合框架的 EnumMap
类提供了一种针对枚举元素的映射实现。
在 EnumMap
中,枚举元素被用 作 键(keys)。它实现了 Map 接口。
在了解 EnumMap
之前,请确保你了解了 Java 枚举。
创建 EnumMap
要创建枚举映射,我们首先需要导入 java.util.EnumMap
包。一旦我们导入了包,下面是在 Java 中创建枚举映射的方法。
enum Size {
SMALL, MEDIUM, LARGE, EXTRALARGE
}
EnumMap<Size, Integer> sizes = new EnumMap<>(Size.class);
在上面的示例中,我们创建了一个名为 sizes
的枚举映射。
这里,
Size
- 枚举的 键(keys),映射到值Integer
- 枚举映射中与相应键关联的 值(values)
EnumMap 的方法
EnumMap
类提供了许多方法,允许我们在枚举映射上执行各种操作。
向 EnumMap 插入元素
put()
- 向枚举映射中插入指定的键/值映射(条目)putAll()
- 将指定映射的所有条目插入到此映射中
例如,
import java.util.EnumMap;
class Main {
enum Size {
SMALL, MEDIUM, LARGE, EXTRALARGE
}
public static void main(String[] args) {
// 创建 Size 枚举的 EnumMap
EnumMap<Size, Integer> sizes1 = new EnumMap<>(Size.class);
// 使用 put() 方法
sizes1.put(Size.SMALL, 28);
sizes1.put(Size.MEDIUM, 32);
System.out.println("EnumMap1: " + sizes1);
EnumMap<Size, Integer> sizes2 = new EnumMap<>(Size.class);
// 使用 putAll() 方法
sizes2.putAll(sizes1);
sizes2.put(Size.LARGE, 36);
System.out.println("EnumMap2: " + sizes2);
}
}
输出
EnumMap1: {SMALL=28, MEDIUM=32}
EnumMap2: {SMALL=28, MEDIUM=32, LARGE=36}
在上面的示例中,我们使用了 putAll()
方法将一个枚举映射 sizes1
的所有元素插入到另一个枚举映射 sizes2
中。
还可以使用 putAll()
将如 HashMap
、TreeMap
等其他映射的元素插入到枚举映射中。但是,所有映射必须是相同的枚举类型。
访问 EnumMap 元素
1. 使用 entrySet(),keySet() 和 values()
entrySet()
- 返回枚举映射中所有键/值映射(条目)的集合keySet()
- 返回枚举映射中所有键的集合values()
- 返回枚举映射中所有值的集合
例如,
import java.util.EnumMap;
class Main {
enum Size {
SMALL, MEDIUM, LARGE, EXTRALARGE
}
public static void main(String[] args) {
// 创建 Size 枚举的 EnumMap
EnumMap<Size, Integer> sizes = new EnumMap<>(Size.class);
sizes.put(Size.SMALL, 28);
sizes.put(Size.MEDIUM, 32);
sizes.put(Size.LARGE, 36);
sizes.put(Size.EXTRALARGE, 40);
System.out.println("EnumMap: " + sizes);
// Using the entrySet() Method
System.out.println("键/值映射: " + sizes.entrySet());
// Using the keySet() Method
System.out.println("键: " + sizes.keySet());
// Using the values() Method
System.out.println("值: " + sizes.values());
}
}
```
**Output**
```java
EnumMap: {SMALL=28, MEDIUM=32, LARGE=36, EXTRALARGE=40}
键/值映射: [SMALL=28, MEDIUM=32, LARGE=36, EXTRALARGE=40]
键: [SMALL, MEDIUM, LARGE, EXTRALARGE]
值: [28, 32, 36, 40]
```
**2. 使用 get() 方法**
`get()` 方法返回与指定键关联的值。如果没有找到指定的键,则返回 `null`。
例如,
```java exec
import java.util.EnumMap;
class Main {
enum Size {
SMALL, MEDIUM, LARGE, EXTRALARGE
}
public static void main(String[] args) {
// 创建 Size 枚举的 EnumMap
EnumMap<Size, Integer> sizes = new EnumMap<>(Size.class);
sizes.put(Size.SMALL, 28);
sizes.put(Size.MEDIUM, 32);
sizes.put(Size.LARGE, 36);
sizes.put(Size.EXTRALARGE, 40);
System.out.println("EnumMap: " + sizes);
// 使用 get() 方法
int value = sizes.get(Size.MEDIUM);
System.out.println("MEDIUM 的值: " + value);
}
}
```
**输出**
```java
EnumMap: {SMALL=28, MEDIUM=32, LARGE=36, EXTRALARGE=40}
MEDIUM 的值: 32
```
## 移除 EnumMap 元素
- `remove(key)` - 返回并移除映射中与指定键关联的条目
- `remove(key, value)` - 只有当指定的键映射到指定的值时,才从映射中移除该条目,并返回布尔值
例如,
```java exec
import java.util.EnumMap;
class Main {
enum Size {
SMALL, MEDIUM, LARGE, EXTRALARGE
}
public static void main(String[] args) {
// 创建 Size 枚举的 EnumMap
EnumMap<Size, Integer> sizes = new EnumMap<>(Size.class);
sizes.put(Size.SMALL, 28);
sizes.put(Size.MEDIUM, 32);
sizes.put(Size.LARGE, 36);
sizes.put(Size.EXTRALARGE, 40);
System.out.println("EnumMap: " + sizes);
// 使用 remove() 方法
int value = sizes.remove(Size.MEDIUM);
System.out.println("移除的值: " + value);
boolean result = sizes.remove(Size.SMALL, 28);
System.out.println("条目 {SMALL=28} 是否移除? " + result);
System.out.println("更新后的 EnumMap: " + sizes);
}
}
```
**输出**
```java
EnumMap: {SMALL=28, MEDIUM=32, LARGE=36, EXTRALARGE=40}
移除的值: 32
条目 {SMALL=28} 是否移除? True
更新后的 EnumMap: {LARGE=36, EXTRALARGE=40}
```
## 替换 EnumMap 元素
- `replace(key, value)` - 将与指定 `key` 关联的值替换为新的 `value`
- `replace(key, old, new)` - 只有当 `old` 值已与指定 `key` 关联时,才将 `old` 值替换为 `new` 值
- `replaceAll(function)` - 将映射中的每个值替换为指定 `function` 的结果
```java exec
import java.util.EnumMap;
class Main {
enum Size {
SMALL, MEDIUM, LARGE, EXTRALARGE
}
public static void main(String[] args) {
// 创建 Size 枚举的 EnumMap
EnumMap<Size, Integer> sizes = new EnumMap<>(Size.class);
sizes.put(Size.SMALL, 28);
sizes.put(Size.MEDIUM, 32);
sizes.put(Size.LARGE, 36);
sizes.put(Size.EXTRALARGE, 40);
System.out.println("EnumMap: " + sizes);
// 使用 replace() 方法
sizes.replace(Size.MEDIUM, 30);
sizes.replace(Size.LARGE, 36, 34);
System.out.println("使用 replace() 后的 EnumMap: " + sizes);
// 使用 replaceAll() 方法
sizes.replaceAll((key, oldValue) -> oldValue + 3);
System.out.println("使用 replaceAll(): " + sizes);
}
}
```
**Output**
```java
EnumMap: {SMALL=28, MEDIUM=32, LARGE=36, EXTRALARGE=40}
使用 replace() 的 EnumMap: {SMALL=28, MEDIUM=30, LARGE=34, EXTRALARGE=40}
使用 replaceAll() 的 EnumMap: {SMALL=31, MEDIUM=33, LARGE=37, EXTRALARGE=43}
```
在上述程序中,请注意以下语句:
```java
sizes.replaceAll((key, oldValue) -> oldValue + 3);
```
在这里,该方法访问了映射的所有条目。然后,使用由[lambda 表达式](/tutorials/java/lambda-expression)提供的新值替换所有值。
## 其他方法
| 方法 | 描述 |
| ----------------- | ---------------------------------------- |
| `clone()` | 创建 `EnumMap` 的副本 |
| `containsKey()` | 搜索指定键在 `EnumMap` 中是否存在,并返回布尔结果 |
| `containsValue()` | 搜索指定值在 `EnumMap` 中是否存在,并返回布尔结果 |
| `size()` | 返回 `EnumMap` 的大小 |
| `clear() ` | 从 `EnumMap` 中删除所有条目 |
## EnumSet 与 EnumMap
无论是 [EnumSet](/tutorials/java/enumset) 还是 `EnumMap` 类都提供了存储枚举值的数据结构。但是,它们之间存在一些重要的区别。
- Enum set 在内部表示为一系列位,而 Enum map 在内部表示为数组。
- Enum set 是使用其预定义方法(如 `allOf()`、`noneOf()`、`of()` 等)创建的。但是,Enum map 是使用其构造函数创建的。
## 可克隆和可序列化接口
`EnumMap` 类还实现了 `Cloneable` 和 `Serializable` 接口。
**Cloneable 接口**
它允许 `EnumMap` 类复制类的实例。
**Serializable 接口**
当需要通过网络传输 Java 对象时,需要将对象转换为位或字节。这是因为 Java 对象不能通过网络传输。
`Serializable` 接口允许类被序列化。这意味着实现 `Serializable` 接口的类的对象可以转换为位或字节。