Java 泛型

一,3种泛型方式:泛型类、泛型接口、泛型方法


泛型类

复制代码
//此处T可以随便写为任意标识,常见的如T、E、K、V等形式的参数常用于表示泛型
//在实例化泛型类时,必须指定T的具体类型
public class Generic<T>{
    private T key;

    public Generic(T key) {
        this.key = key;
    }

    public T getKey(){
        return key;
    }
}

泛型接口

复制代码
public interface Generator<T> {
    public T next();
}

// 实现泛型接口时,可以传入或者不传实际类型:
public class FruitGenerator<T> implements Generator<T>
public class FruitGenerator implements Generator<String>

泛型方法

复制代码
// 只有声明了<T>的方法才是泛型方法,泛型类中的使用了泛型的成员方法并不是泛型方法
// 此处T可以随便写为任意标识,常见的如T、E、K、V等形式的参数常用于表示泛型
public <T> T genericMethod(Class<T> tClass) {
        T instance = tClass.newInstance();
        return instance;
}
  • 静态方法要使用泛型的话,必须将静态方法也定义成泛型方法

    public class StaticGenerator<T> {
    public static <T> void show(T t){

    复制代码
      }

    }

  • 泛型方法中添加上下边界的时候,必须在权限声明与返回值之间的<T>上添加上下边界,即在泛型声明的时候添加。

    // 编译器会报错
    public <T> T showKeyName(Generic<T extends Number> container)

    public <T extends Number> T showKeyName(Generic<T> container){
    System.out.println("container key :" + container.getKey());
    T test = container.getKey();
    return test;
    }

二,Tips


1,类型擦除:泛型类型只在编译阶段有效。
2,不能创建一个确切类型的泛型数组,而使用通配符?是可以的。

  • ❌\] List\\[\] ls = new ArrayList\\[10

  • ✅\] List\\[\] ls = new ArrayList\\[10\];

3,无法对泛型代码直接使用 instanceof 关键字,而使用通配符?是可以的。

  • ❌\] list instanceof ArrayList\

4,注意两种继承情况
① 第一种

复制代码
public void showKeyValue(Generic<Number> obj){
    Log.d("泛型测试","key value is " + obj.getKey());
}

Generic<Integer> gInteger = new Generic<Integer>(123);
Generic<Number> gNumber = new Generic<Number>(456);

[✅] showKeyValue(gNumber);
[❌] showKeyValue(gInteger); //编译报错

② 第二种

复制代码
class Fruit {
    @Override
    public String toString() {
        return "fruit";
    }
}

class Apple extends Fruit {
    @Override
    public String toString() {
        return "apple";
    }
}

class GenerateTest<T> {
    public void show_1(T t) {
        System.out.println(t.toString());
    }
}

public static void main(String[] args) {
    Apple apple = new Apple();
    GenerateTest<Fruit> generateTest = new GenerateTest<Fruit>();
    //apple是Fruit的子类,所以这里可以
    [✅]generateTest.show_1(apple);
}    
相关推荐
biter down25 分钟前
C 语言11:输入方法全解析
c语言·开发语言
.格子衫.5 小时前
Spring Boot 原理篇
java·spring boot·后端
多云几多5 小时前
Yudao单体项目 springboot Admin安全验证开启
java·spring boot·spring·springbootadmin
Jabes.yang8 小时前
Java求职面试实战:从Spring Boot到微服务架构的技术探讨
java·数据库·spring boot·微服务·面试·消息队列·互联网大厂
聪明的笨猪猪8 小时前
Java Redis “高可用 — 主从复制”面试清单(含超通俗生活案例与深度理解)
java·经验分享·笔记·面试
执尺量北斗8 小时前
[特殊字符] 基于 Qt + OpenGL 实现的入门级打砖块游戏
开发语言·qt·游戏
夏子曦8 小时前
C#内存管理深度解析:从栈堆原理到高性能编程实践
开发语言·c#
兮动人8 小时前
Spring Bean耗时分析工具
java·后端·spring·bean耗时分析工具
MESSIR228 小时前
Spring IOC(控制反转)中常用注解
java·spring
摇滚侠8 小时前
Spring Boot 3零基础教程,Demo小结,笔记04
java·spring boot·笔记