WeakHashMap
类是 Java 集合框架 中的一部分,提供了哈希表数据结构的功能。
它实现了 Map 接口。
注意:WeakHashMap 的键是 WeakReference 类型。
在 Java 中,如果一个弱引用对象不再被程序使用,它可以被垃圾回收。
让我们先学习如何创建一个弱哈希表。然后,我们将学习它与哈希表有何不同。
创建 WeakHashMap
为了创建弱哈希表,我们必须首先导入 java.util.WeakHashMap
包。导入包后,我们可以在 Java 中这样创建弱哈希表。
//WeakHashMap creation with capacity 8 and load factor 0.6
WeakHashMap<Key, Value> numbers = new WeakHashMap<>(8, 0.6);
在上面的代码中,我们创建了一个名为 numbers 的弱哈希表。
这里,
- Key - 用于将 map 中的每个元素(值)关联起来的唯一标识符
- Value - 由键在 map 中关联的元素
注意 new WeakHashMap<>(8, 0.6)
这部分。在这里,第一个参数是 **容量**,第二个参数是 **加载因子**。
- 容量 - 此映射的容量为 8。这意味着它可以存储 8 个条目。
- 加载因子 - 此映射的加载因子为 0.6。这意味着当我们的哈希表填满了 60% 时,条目将被移动到一个容量是原始哈希表两倍的新哈希表中。
默认容量和加载因子
也可以不定义容量和加载因子来创建弱哈希表。例如,
// WeakHashMap with default capacity and load factor
WeakHashMap<Key, Value> numbers1 = new WeakHashMap<>();
默认情况下,
- 映射的容量将是 16
- 加载因子将为0.75
HashMap 和 WeakHashMap 之间的区别
让我们看看 Java 中弱哈希表的实现。
import java.util.WeakHashMap;
class Main {
public static void main(String[] args) {
// Creating WeakHashMap of numbers
WeakHashMap<String, Integer> numbers = new WeakHashMap<>();
String two = new String("Two");
Integer twoValue = 2;
String four = new String("Four");
Integer fourValue = 4;
// Inserting elements
numbers.put(two, twoValue);
numbers.put(four, fourValue);
System.out.println("WeakHashMap: " + numbers);
// Make the reference null
two = null;
// Perform garbage collection
System.gc();
System.out.println("WeakHashMap after garbage collection: " + numbers);
}
}
输出
WeakHashMap: {Four=4, Two=2} WeakHashMap after garbage collection: {Four}
正如我们所见,当弱哈希表的键 two 被设置为 null
并执行垃圾回收时,该键会被移除。
这是因为与哈希表不同,弱哈希表的键是 **弱引用** 类型。这意味着,如果映射中的某个键不再被使用,该映射的条目将被垃圾回收器移除。这有助于节省资源。
现在让我们在哈希表中看看相同的实现。
import java.util.HashMap;
class Main {
public static void main(String[] args) {
// Creating HashMap of even numbers
HashMap<String, Integer> numbers = new HashMap<>();
String two = new String("Two");
Integer twoValue = 2;
String four = new String("Four");
Integer fourValue = 4;
// Inserting elements
numbers.put(two, twoValue);
numbers.put(four, fourValue);
System.out.println("HashMap: " + numbers);
// Make the reference null
two = null;
// Perform garbage collection
System.gc();
System.out.println("HashMap after garbage collection: " + numbers);
}
}
输出
HashMap: {Four=4, Two=2} HashMap after garbage collection: {Four=4, Two=2}
在这里,当哈希表的键 two 被设置为 null
并执行垃圾回收时,该键不会被移除。
这是因为与弱哈希表不同,哈希表的键是 **强引用** 类型。这意味着,即使映射中的某个键不再被使用,该映射的条目也不会被垃圾回收器移除。
注意:HashMap 和 WeakHashMap 的所有功能都相似,只是 WeakHashMap 的键是弱引用类型,而 HashMap 的键是强引用类型。
从其他 Map 创建 WeakHashMap
下面是如何从其他 Map 创建弱哈希表。
import java.util.HashMap;
import java.util.WeakHashMap;
class Main {
public static void main(String[] args) {
// Creating a hashmap of even numbers
HashMap<String, Integer> evenNumbers = new HashMap<>();
String two = new String("Two");
Integer twoValue = 2;
evenNumbers.put(two, twoValue);
System.out.println("HashMap: " + evenNumbers);
// Creating a weak hash map from other hashmap
WeakHashMap<String, Integer> numbers = new WeakHashMap<>(evenNumbers);
System.out.println("WeakHashMap: " + numbers);
}
}
输出
HashMap: {Two=2} WeakHashMap: {Two=2}
WeakHashMap 的方法
WeakHashMap
类提供了允许我们对映射执行各种操作的方法。
向 WeakHashMap 插入元素
put()
- 将指定的键/值映射插入到映射中putAll()
- 将指定映射中的所有条目插入到此映射中putIfAbsent()
- 如果指定键不在映射中,则将指定的键/值映射插入到映射中
例如,
import java.util.WeakHashMap;
class Main {
public static void main(String[] args) {
// Creating WeakHashMap of even numbers
WeakHashMap<String, Integer> evenNumbers = new WeakHashMap<>();
String two = new String("Two");
Integer twoValue = 2;
// Using put()
evenNumbers.put(two, twoValue);
String four = new String("Four");
Integer fourValue = 4;
// Using putIfAbsent()
evenNumbers.putIfAbsent(four, fourValue);
System.out.println("WeakHashMap of even numbers: " + evenNumbers);
//Creating WeakHashMap of numbers
WeakHashMap<String, Integer> numbers = new WeakHashMap<>();
String one = new String("One");
Integer oneValue = 1;
numbers.put(one, oneValue);
// Using putAll()
numbers.putAll(evenNumbers);
System.out.println("WeakHashMap of numbers: " + numbers);
}
}
输出
WeakHashMap of even numbers: {Four=4, Two=2} WeakHashMap of numbers: {Two=2, Four=4, One=1}
访问 WeakHashMap 元素
1. 使用 entrySet()、keySet() 和 values()
entrySet()
- 返回映射中所有键/值映射的集合keySet()
- 返回映射中所有键的集合values()
- 返回映射中所有值的集合
例如,
import java.util.WeakHashMap;
class Main {
public static void main(String[] args) {
// Creating WeakHashMap of even numbers
WeakHashMap<String, Integer> numbers = new WeakHashMap<>();
String one = new String("One");
Integer oneValue = 1;
numbers.put(one, oneValue);
String two = new String("Two");
Integer twoValue = 2;
numbers.put(two, twoValue);
System.out.println("WeakHashMap: " + numbers);
// Using entrySet()
System.out.println("Key/Value mappings: " + numbers.entrySet());
// Using keySet()
System.out.println("Keys: " + numbers.keySet());
// Using values()
System.out.println("Values: " + numbers.values());
}
}
输出
WeakHashMap: {Two=2, One=1} Key/Value mappings: [Two=2, One=1] Keys: [Two, One] Values: [1, 2]
2. 使用 get() 和 getOrDefault()
get()
- 返回与指定键关联的值。如果找不到键,则返回null
。getOrDefault()
- 返回与指定键关联的值。如果找不到键,则返回指定的默认值。
例如,
import java.util.WeakHashMap;
class Main {
public static void main(String[] args) {
// Creating WeakHashMap of even numbers
WeakHashMap<String, Integer> numbers = new WeakHashMap<>();
String one = new String("One");
Integer oneValue = 1;
numbers.put(one, oneValue);
String two = new String("Two");
Integer twoValue = 2;
numbers.put(two, twoValue);
System.out.println("WeakHashMap: " + numbers);
// Using get()
int value1 = numbers.get("Two");
System.out.println("Using get(): " + value1);
// Using getOrDefault()
int value2 = numbers.getOrDefault("Four", 4);
System.out.println("Using getOrDefault(): " + value2);
}
}
输出
WeakHashMap: {Two=2, One=1} Using get(): 2 Using getOrDefault(): 4
移除 WeakHashMap 元素
remove(key)
- 返回并从映射中移除与指定键关联的条目remove(key, value)
- 仅当指定键映射到指定值时才从映射中移除该条目,并返回一个布尔值
例如,
import java.util.WeakHashMap;
class Main {
public static void main(String[] args) {
// Creating WeakHashMap of even numbers
WeakHashMap<String, Integer> numbers = new WeakHashMap<>();
String one = new String("One");
Integer oneValue = 1;
numbers.put(one, oneValue);
String two = new String("Two");
Integer twoValue = 2;
numbers.put(two, twoValue);
System.out.println("WeakHashMap: " + numbers);
// Using remove() with single parameter
int value = numbers.remove("Two");
System.out.println("Removed value: " + value);
// Using remove() with 2 parameters
boolean result = numbers.remove("One", 3);
System.out.println("Is the entry {One=3} removed? " + result);
System.out.println("Updated WeakHashMap: " + numbers);
}
}
输出
WeakHashMap: {Two=2, One=1} Removed value: 2 Is the entry {One=3} removed? false Updated WeakHashMap: {One=1}
WeakHashMap 的其他方法
方法 | 描述 |
---|---|
clear() |
从映射中移除所有条目 |
containsKey() |
检查映射是否包含指定键,并返回一个布尔值 |
containsValue() |
检查映射是否包含指定值,并返回一个布尔值 |
size() |
返回映射的大小 |
isEmpty() |
检查映射是否为空,并返回一个布尔值 |
要了解更多信息,请访问 Java WeakHashMap (官方 Java 文档)。