Java泛型

泛型简介

泛型是Java 5引入的一个重要特性,它允许在定义类、接口和方法时使用类型参数。泛型的主要目的是提供编译时类型安全,并消除类型转换的需要。

泛型的基本概念

// 泛型类定义 public class Box { private T content; public void setContent(T content) { this.content = content; } public T getContent() { return content; } } // 使用泛型类 Box stringBox = new Box<>(); stringBox.setContent("Hello"); String message = stringBox.getContent();

泛型类

泛型类是在类定义时使用类型参数的类。

// 泛型类示例 public class Pair { private K key; private V value; public Pair(K key, V value) { this.key = key; this.value = value; } public K getKey() { return key; } public V getValue() { return value; } public void setKey(K key) { this.key = key; } public void setValue(V value) { this.value = value; } } // 使用泛型类 Pair pair = new Pair<>("age", 25); String key = pair.getKey(); Integer value = pair.getValue();

泛型方法

泛型方法是在方法定义时使用类型参数的方法。

// 泛型方法示例 public class ArrayUtils { public static void swap(T[] array, int i, int j) { T temp = array[i]; array[i] = array[j]; array[j] = temp; } public static T getFirst(T[] array) { return array.length > 0 ? array[0] : null; } } // 使用泛型方法 String[] names = {"Alice", "Bob", "Charlie"}; ArrayUtils.swap(names, 0, 2); String first = ArrayUtils.getFirst(names);

有界类型参数

有界类型参数允许限制泛型类型参数的范围。

// 有界类型参数示例 public class NumberBox { private T number; public NumberBox(T number) { this.number = number; } public double getDoubleValue() { return number.doubleValue(); } public int getIntValue() { return number.intValue(); } } // 使用有界类型参数 NumberBox intBox = new NumberBox<>(42); NumberBox doubleBox = new NumberBox<>(3.14); // 编译错误:String不是Number的子类 // NumberBox stringBox = new NumberBox<>("error");

通配符

通配符用于表示未知类型,使泛型更加灵活。

// 通配符示例 public class WildcardExample { // 上界通配符 public static double sumOfList(List list) { double sum = 0.0; for (Number number : list) { sum += number.doubleValue(); } return sum; } // 下界通配符 public static void addNumbers(List list) { list.add(1); list.add(2); list.add(3); } } // 使用通配符 List integers = Arrays.asList(1, 2, 3); List doubles = Arrays.asList(1.1, 2.2, 3.3); double sum1 = WildcardExample.sumOfList(integers); double sum2 = WildcardExample.sumOfList(doubles); List numbers = new ArrayList<>(); WildcardExample.addNumbers(numbers);

泛型接口

泛型接口允许在接口定义时使用类型参数。

// 泛型接口示例 public interface Comparable { int compareTo(T other); } // 实现泛型接口 public class Person implements Comparable { private String name; private int age; public Person(String name, int age) { this.name = name; this.age = age; } @Override public int compareTo(Person other) { return this.age - other.age; } }

实践练习

练习1:实现泛型栈

public class Stack {
    private List elements;
    
    public Stack() {
        elements = new ArrayList<>();
    }
    
    public void push(T element) {
        elements.add(element);
    }
    
    public T pop() {
        if (isEmpty()) {
            throw new EmptyStackException();
        }
        return elements.remove(elements.size() - 1);
    }
    
    public T peek() {
        if (isEmpty()) {
            throw new EmptyStackException();
        }
        return elements.get(elements.size() - 1);
    }
    
    public boolean isEmpty() {
        return elements.isEmpty();
    }
    
    public int size() {
        return elements.size();
    }
}