Java基础——泛型

泛型

泛型介绍

  1. 泛型又称参数化类型,是jdk5.0出现的新特性,解决数据类型的安全性问题。
  2. 在类声明或实例化时只要指定好需要的具体的类型即可。
  3. Java泛型可以保证如果程序在编译时没有发出警告,运行时就不会产生。
  4. 泛型的作用:可以在类声明时通过一个标识表示类中某个属性的类型,或者某个方法的返回值类型,或是参数类型。

# 常见的泛型的类型表示

上面的 T 仅仅类似一个形参的作用,名字实际上是可以任意起的,但是我们写代码总该是要讲究可读性的。常见的参数通常有 :

  1. E - Element (在集合中使用,因为集合中存放的是元素)

  2. T - Type(表示Java 类,包括基本的类和我们自定义的类)

  3. K - Key(表示键,比如Map中的key)

  4. V - Value(表示值,如Map中的value)

  5. ? - (表示不确定的java类型)

泛型使用细节

package com.study.srv.demo15;

import java.util.ArrayList;

/**
 * @author Wen先森
 * @version 1.0
 * @date 2022/4/11 17:23
 */
public class Demo04 {
    public static void main(String[] args) {
        //1.用泛型指向数据类型时,要求是引用类型,不能是基本类型
        ArrayList<String> list = new ArrayList<>();
//        ArrayList<int> ints = new ArrayList<int>();
        //2.在给泛型指定了具体类型之后,可以传入该类型或者其他子类类型。
        Son<A> aSon = new Son<A>(new A());
        Son<A> bSon = new Son<A>(new B());
        aSon.f();
        bSon.f();
        //3.泛型的使用形式
        ArrayList<Integer> list1 = new ArrayList<Integer>();
        //在实际开发中,我们往往简写,编译器会自动进行类型判断。
        ArrayList<Integer> list2 = new ArrayList<>();
        //4.如果不写<>。泛型默认是Object
        ArrayList list3 = new ArrayList();
    }
}
class A{}
class B extends A{}
class Son<E>{
    E e;

    public Son(E e) {
        this.e = e;
    }
    public void f(){
        System.out.println(e.getClass());
    }
}

自定义泛型

基本语法:

class 类名<T,R...>{//...表示可以有多个泛型

成员

}

  1. 普通成员可以使用泛型(属性、方法)。
  2. 使用泛型的数组,不能初始化(因为数组在new时不能确定类型,无法开辟空间)。
  3. 静态方法中不能使用类的泛型(因为静态是和类相关的,在类加载时,对象还没有创建而泛型则是在类创建定义的时候才会指定类型)。
  4. 泛型类的类型,是在创建对象时确定的(因为创建对象时,需要指定确定类型)。
  5. 如果在创建对象时,没有指定类型,默认object。

自定义泛型接口

基本语法:

interface 接口名<T,R...>{

  1. 接口中,静态成员也不能使用泛型(这和泛型类的规定一样)。
  2. 泛型接口的类型,在继承接口或者实现接口时确定。
  3. 没有指定类型,默认为object。
  4. 泛型方法,可以定义在普通类中,也可以定义在泛型类中。
  5. 当泛型方法被调用时,类型会确定。
  6. 当public void eat(E e){},修饰符没有<T,R...>eat方法不是泛型方法,而是使用了泛型。
package com.study.srv.demo15;

/**
 * @author Wen先森
 * @version 1.0
 * @date 2022/4/24 14:21
 * 泛型方法使用
 */
public class Demo09 {
    public static void main(String[] args) {
        Car car = new Car();
        System.out.println("调用car.f1方法:");
        car.f1("测试",12);
        System.out.println("调用car.f1方法:");
        car.f1(12.00,'c');
        Pig<String, Integer> pig = new Pig<>();
        System.out.println("调用pig.f1方法:");
        pig.f1(2,33);
        System.out.println("调用pig.f2方法:");
        pig.f2("?");
        System.out.println("调用pig.f3方法:");
        pig.f3('l',"随便");
    }
}
class Car{
    public void run(){
        //普通方法
    }
    //1.<M,N>就是泛型
    //2.提供给f1方法使用的
    public <M,N> void f1(M m,N n){
        //泛型方法
        System.out.println(m.getClass());
        System.out.println(n.getClass());
    }
}
class Pig<T,R>{//泛型类
    public void run(){
        //普通方法
    }
    public <L,J> void f1(L l,J j){
        //泛型方法
        System.out.println(l.getClass());
        System.out.println(j.getClass());
    }
    //1.f2不是泛型方法
    //2.而是f2使用了类声明的泛型
    public void f2(T t){
        System.out.println(t.getClass());
    }
    //泛型方法,可以使用类声明的泛型,也可以使用自己声明的泛型。
    public<K,J> void f3(K k,J j){
        System.out.println(k.getClass());
        System.out.println(j.getClass());
    }
}

 泛型的继承和通配符

  1. 泛型不具备继承性
  2. <?>:支持任意泛型类型
  3. <?extends A>:支持A类以及A类的子类,规定了泛型的上线
  4. <? super A>:支持A类以及A类的父类,不限于直接父类,规定了泛型的下限

 

package com.study.srv.demo15;

import java.util.ArrayList;
import java.util.List;

/**
 * @author Wen先森
 * @version 1.0
 * @date 2022/4/24 16:17
 */
public class Demo10 {
    public static void main(String[] args) {
        Object o = new String("xx");

        //泛型没有继承性
        //List<Object> list = new ArrayList<String>();

        List<Object> list1 = new ArrayList<>();
        List<String> list2 = new ArrayList<>();
        List<A1> list3 = new ArrayList<>();
        List<B1> list4 = new ArrayList<>();
        List<C1> list5 = new ArrayList<>();


        //如果是List<?>c,可以接受任意的泛型数据
        printCollection1(list1);    //√
        printCollection1(list2);    //√
        printCollection1(list3);    //√
        printCollection1(list4);    //√
        printCollection1(list5);    //√

        //如果是List<? extends A1>c,表示上限,可以接受A1或者A1的子类
//        printCollection2(list1);  //×
//        printCollection2(list2);  //×
        printCollection2(list3);    //√
        printCollection2(list4);    //√
        printCollection2(list5);    //√


        //如果是List<? super A1>c,表示下限,可以接受A1或者A1的父类,不限于直接父类
        printCollection3(list1);    //√
//        printCollection3(list2);    //×
        printCollection3(list3);    //√
//        printCollection3(list4);    //×
//        printCollection3(list5);    //×


    }

    public static void printCollection1(List<?> c) {
        for (Object object : c) {
            System.out.println(object);
        }
    }

    public static void printCollection2(List<? extends A1> c) {
        for (Object object : c) {
            System.out.println(object);
        }
    }

    public static void printCollection3(List<? super A1> c) {
        for (Object object : c) {
            System.out.println(object);
        }
    }
}
class A1{}
class B1 extends A1{}
class C1 extends B1{}

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

Wen先森

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值