泛型
泛型是 Java 5 引入的特性,它允许在定义类、接口、方法时使用类型参数,在创建对象或调用方法时再传入具体的类型
基本定义
泛型类
java
// 定义泛型类
public class Box<T> { // T 是类型参数
private T content;
public Box(T content) {
this.content = content;
}
public T getContent() {
return content;
}
public void setContent(T content) {
this.content = content;
}
}
// 使用泛型类
Box<String> stringBox = new Box<>("Hello");
Box<Integer> intBox = new Box<>(123);
String str = stringBox.getContent(); // 不需要转换
泛型方法
java
public class Util {
// 泛型方法 - 在返回类型前声明 <T>
public static <T> T getMiddle(T[] array) {
return array[array.length / 2];
}
// 多个类型参数
public static <K, V> V getValue(Map<K, V> map, K key) {
return map.get(key);
}
// 在普通类中的泛型方法
public <E> void printArray(E[] array) {
for (E element : array) {
System.out.println(element);
}
}
}
// 使用
String[] names = {"Alice", "Bob", "Charlie"};
String middle = Util.getMiddle(names); // 自动推断为 String
Integer[] numbers = {1, 2, 3, 4, 5};
Integer midNum = Util.getMiddle(numbers); // 自动推断为 Integer
泛型接口
java
// 定义泛型接口
public interface Pair<K, V> { // 多个类型参数
K getKey();
V getValue();
}
// 实现泛型接口
public class OrderedPair<K, V> implements Pair<K, V> {
private K key;
private V value;
public OrderedPair(K key, V value) {
this.key = key;
this.value = value;
}
public K getKey() { return key; }
public V getValue() { return value; }
}
// 使用
Pair<String, Integer> pair = new OrderedPair<>("age", 25);
String key = pair.getKey();
Integer value = pair.getValue();
java
// 错误:编译不通过
public T getCacheObject(String key) // 错误!编译器不知道 T 是什么
// 正确:需要先声明泛型类型
public <T> T getCacheObject(String key) // 先声明 <T>,再使用 T
java
public <T> T getCacheObject(final String key)
// ↑ ↑
// 声明 返回类型
// 泛型 泛型
java
// 声明一个泛型类型 T
public <T> T getCacheObject(String key)
// 等价于:
public Object getCacheObject(String key) // 非泛型版本需要强制转换
java
// 多个泛型参数
public <K, V> V getFromMap(final K key, final Map<K, V> map) {
return map.get(key);
}
// 使用
String value = getFromMap("name", nameMap);
Integer number = getFromMap("count", countMap);
小知识: 形参用final修饰代表传参不能被修改