java 泛型

目录

 

1. 泛型类、泛型方法

2.泛型中extends 和 super的区别

2.1 extends

2.2 super

  3. 基本原理


1. 泛型类、泛型方法

类名<T>、类名<T,  S>  泛型类的声明形式就是这样的,<>里面就是泛型类型变量,可以是一个,也可以是多个,用于代表任意一种类型。 建议:泛型类型变量用大写形式,且比较短,不一定非是一个大写字母,但是建议最好这样遵循,在java库中,使用E表示集合的元素类型,K和V分别表示映射的键与值类型,T表示任意类型。  举个例子:

public class HeHe<T, s, AAR> {
    private T alice;
    private s bob;
    private AAR manry;
    public HeHe(){}
    public void prin(T content){
        System.out.print(content);
    }

    public T getAlice() { return alice; }
    public void setAlice(T alice) { this.alice = alice; }
    public s getBob() { return bob; }
    public void setBob(s bob) { this.bob = bob; }
    public AAR getManry() { return manry; }
    public void setManry(AAR manry) { this.manry = manry; }

    public static void main(String[] args){
        HeHe<String, Integer, Date> he = new HeHe<>();
        he.setAlice("my name is alice");
        he.setBob(12);
        he.setManry(new Date());
    }
}

泛型方法:将泛型类型变量紧挨着返回类型并放在返回类型的前面。比如:public <T> int getAa(){  }

泛型方法可以定义在普通类中,也可以定义在泛型类中,调用泛型方法时,在方法名前面的尖括号中放入具体类型

int  var =  <String>getAa();

但是泛型的使用需要注意:泛型可以是任意的类型,当需要比较的时候,如果具体的类型没有实现了Comparable接口的compareTo方法,那么就会报错或者得到一个不正确的结果。

解决方法: public <T extends Comparable> int  getAa(){   }

2.泛型中extends 和 super的区别

这里只是针对没有使用强制类型转换的,在此基础上,才有下面的说明,如果使用强制类型转换,那下面的说明就不严谨了。

2.1 extends

类型的上界,只接收本身类或者其子类的引用赋值,比如List<? extends Fruit> list 如下。

只能接收取值,而不能插入值,因为List<? extends Fruit> list 可以接收的Fruit类或者子类,但是编译器不知道具体是哪个类。

只能list.add(null) 没有意义。

public class Fruit{}
public class Apple extends Fruit{}
public class Banana extends Fruit{}
//main方法
public static void main(String[] args){
    List<? extends Fruit> list = new ArrayList<>();
    //List<? extends Fruit> list = new ArrayList<Apple>(); 这样也行
    //List<? extends Fruit> list = new ArrayList<Banana>(); 这样也行
    //extends用法规定:只准取数据,不能存入数据,除非你用强制类型转换
}

2.2 super

类型的下界,只接受本身类或者其父类的引用赋值,比如List<? extends Fruit> list 如下。

只能插入值,不能获取值,插入值也只能时Fruit这个下界类本身或者下界类的子类对象,不能获取值是因为不知道获取到的对象属于哪个类,但是可以Object o = list.get(1); 这种方法类获取对象,但是Object类引用会丢失实际对象的所有值,没意义。

public class Food{}
public class Fruit extends Food{}
public class Apple extends Fruit{}
public class Banana extends Fruit{}
//main方法
public static void main(String[] args){
    List<? extends Fruit> list = new ArrayList<Food>();
    list.add(new Fruit());
    list.add(new Apple());
    //List<? extends Apple> list = new ArrayList<Food>(); 这样也行
    //List<? extends Apple> list = new ArrayList<Fruit>(); 这样也行
    //super用法规定:只准存入数据,不能取数据
}

  3. 基本原理

泛型这个概念只停留在编译阶段,因为JVM是不认识泛型的,比如上文中定义了HeHe<T, s, AAR> 类,假如我们在某个代码中用到了,HeHe<String, Integer, Long> hehe = new HeHe<>(); 这样的话,编译器就会将根据具体的类型去将所有的泛型符号替换掉,如果HeHe hehe = new HeHe(); 是这样的话,那么就用Object去替换掉所有的泛型符号,这种替换就叫作“类型擦除”。

所以说,泛型只停留于编译阶段,编译完了后,就是实实在在的类型了。

 

  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值