泛型的上界指定了类型参数必须是某个类的子类或者实现了某个接口。它的语法形式为 T extends B
,其中T是泛型类型参数,B是上界类型。例如,下面的代码展示了一个泛型类 Box
,它的类型参数T必须是 Number
或其子类:
public class Box<T extends Number> { private T value; public Box(T value) { this.value = value; } public T getValue() { return value; } }
在上面的代码中,我们使用了 extends
关键字来指定泛型类型参数的上界类型,这意味着泛型类型参数必须是 Number
或其子类。这样,我们就可以使用 Box
类来存储 Integer
、Double
、Float
等类型的值,因为它们都是 Number
的子类。另外,通过使用泛型的上界,我们可以确保 Box
类的实例中只存储 Number
类型的值,避免了类型转换异常的风险。
在使用泛型的时候,如果我们传入一个类型不符合上界限制的参数,则会在编译时发生错误,例如:
Box<String> box = new Box<>("Hello World"); // 编译错误:String 不是 Number 的子类
泛型的下界指定了类型参数必须是某个类的超类或者是某个接口的实现类。它的语法形式为 T super B
,其中T是泛型类型参数,B是下界类型。下面是一个示例,展示了一个泛型类 Box
,它的类型参数T必须是 Object
或其超类:
public class Box<T super Object> { private T value; public Box(T value) { this.value = value; } public T getValue() { return value; } }
在上面的代码中,我们使用了 super
关键字来指定泛型类型参数的下界类型,这意味着泛型类型参数必须是 Object
或其超类。这样,我们就可以使用 Box
类来存储 Object
、String
、Integer
、Double
等类型的值,因为它们都是 Object
的子类。另外,通过使用泛型的下界,我们可以确保 Box
类的实例中存储的值都是 Object
类型,避免了类型转换异常的风险。
在使用泛型的时候,如果我们传入一个类型不符合下界限制的参数,则会在编译时发生错误,例如:
Box<Integer> box = new Box<>(123); // 编译错误:Integer 不是 Object 的超类
有时候,我们需要在泛型中同时使用上界和下界的限制,此时可以使用通配符 ?
来表示未知类型。例如,下面的代码展示了一个泛型方法 copy
,它可以将一个数组的元素复制到另一个数组中:
public static <T> void copy(List<? extends T> src, List<? super T> dest) { for (T t : src) { dest.add(t); } }
在上面的代码中,我们使用了通配符 ?
来表示未知类型,它可以同时满足 src
参数是 T
类型或其子类,dest
参数是 T
类型或其超类的限制条件。这样,我们就可以将任意类型的元素复制到另一个列表中了。通过使用上下界通配符,我们可以更加灵活地定义泛型方法,同时保证类型安全。
以上是Java泛型的上界和下界通配符怎么使用的详细内容。更多信息请关注PHP中文网其他相关文章!