Java基础之:自定义泛型

Java基础之:自定义泛型

自定义泛型的细节:

  1. 普通成员可以使用泛型(属性与方法)

  2. 使用泛型的数组不可初始化

  3. 静态方法中不可使用类的泛型

  4. 泛型类的类型,是在创建对象时确定的(因为创建对象时,需要指定确定类型)

  5. 如果在创建对象时,没有指定类型,默认为Object

package class_Generic_custom;
​
public class ClassTest01_customGeneric {
    public static void main(String[] args) {
        //可以在自定义类或接口中使用泛型
        AA<String> a = new AA<>("hi");
        a.say();//String
        
        //这里使用Integer,而不是int。因为泛型接收传入的类型只能是引用类型。
        AA<Integer> b = new AA<>(123);  
        b.say();//Integer
    }
}
class AA<T>{    //泛型一般使用T来表示,type。
    private T t;    //创建T类型的属性 t
    public void say() {
        System.out.println(t.getClass()); //返回t的类型
    }
    public AA(T t) {
        this.t = t;
    }
}
​
class BB<E,T>{  //泛型可以有多个
    E e;
    T t;
    
//  public static E es;//泛型不可以使用static修饰,因为泛型是在创建对象是传入的。
    
    
    
    //使用泛型的数组,不能初始化
    E[] eArr /*= new E[6]*/; //报错:Cannot create a generic array of E
    public void seteArr(E[] arr) {  //使用set方法传入参数来定义泛型数组,或构造器
        eArr = arr;
    }
    
    //静态方法中不能使用类的泛型
//  public static void show(E e) { //报错:Cannot make a static reference to the non-static type E
        //静态方法使用时,可能并没有创建对象,那么e的类型也无法确定
//  }
}

  

 

自定义泛型接口

  1. 接口中,静态成员也不能使用泛型(这个和泛型类规定一样)

  2. 泛型接口的类型, 在接口被扩展时(即:被继承或者实现) 会确定 [后面举例]

  3. 没有指定类型,默认为Object [后面举例]

package class_Generic_custom;
public class ClassTest04_GenericInterface {
    public static void main(String[] args) {
    }
}
​
//自定义泛型接口
interface IA<T>{
    public T show();    //返回T类型的数据
}
​
//若有类实现了泛型接口,那么在继承的时候  就需要指定泛型。
class IIAA implements IA<String>{   
    @Override
    public String show() {
        return "IIAA";
    }
}
​
​
//若有类实现了泛型接口,但此类本身也时泛型类,可以在创建类时不指定接口的泛型。
//将类的泛型传递给接口。
class BBB<E> implements IA<E>{
​
    @Override
    public E show() {
        return null;
    }
}
​
class CC<K>{
    
}
​
//若既继承了泛型父类,又实现了泛型接口,可以分别为它们传递泛型
//也可以像上面一样使用一个泛型,传递给它们。
class DD<E,T,V> extends CC<E> implements IA<T>{
    @Override
    public T show() {
        return null;
    }
}

 

自定义泛型方法

1) 泛型方法,可以定义在普通类中, 也可以定义在泛型类中

2) 当泛型方法被调用时,类型会确定.

package class_Generic_custom;
​
public class ClassTest03_GenericMethods {
​
    public static void main(String[] args) {
        MM<String> m = new MM<>();
        m.show(123);//Integer
        m.say(new Object());//Object
    }
​
}
class MM<T>{
    //自定义泛型方法
    public<E> void show(E e) {
        System.out.println(e.getClass());//返回E,即E是什么类型传入,那么输出就是什么类型
    }
    
    //当泛型类与自定义泛型方法使用的泛型重名时,采用就近原则
    public<T> void say(T t) {
        System.out.println(t.getClass());
    }
    
}

泛型的继承和通配符

说明

1.泛型不具有继承性,例如:
List<Object> list = new ArrayList<String>(); //×
2.<?>:表示支持任意泛型类型
3.<? extends A>:表示支持A类以及A类的子类,规定了泛型的上限
4.<? super A>:表示支持支持A类以及A类的父类,不限于直接父类,规定了泛型的下限。

package class_Generic_custom;
​
import java.util.ArrayList;
​
public class ClassTest02_ExtendsGeneric {
​
    public static void main(String[] args) {
        
        // 泛型不具备继承性
        // ArrayList<Object> list = new ArrayList<String>();
        
        ArrayList<Object> list1 = new ArrayList<>();
        ArrayList<String> list2 = new ArrayList<>();
        ArrayList<Grandpa> list3 = new ArrayList<>();
        ArrayList<Father> list4 = new ArrayList<>();
        ArrayList<Son> list5 = new ArrayList<>();
        
//      print(list1);//X    //Object 不属于 Father及其子类
//      print(list2);//X    //String 不属于 Father及其子类
//      print(list3);//X    //Grandpa 属于 Father 父类
//      print(list4);//√
//      print(list5);//√
    
//      print2(list1);//√
//      print2(list2);//X   //String 不属于 Father及其父类
//      print2(list3);//√
//      print2(list4);//√
//      print2(list5);//X   //Son 属于 Father子类
        
//      print3(list1);//√
//      print3(list2);//√
//      print3(list3);//√
//      print3(list4);//√
//      print3(list5);//√
​
    }
    
    public static void print(ArrayList<? extends Father> e) {
        
    }
    
    public static void print2(ArrayList<? super Father> e) {
        
    }
    public static void print3(ArrayList<?> e) {
        
    }
}
​
class Grandpa{
    public void hi() {
        System.out.println("hi~");
    }
}
​
class Father extends Grandpa{   
    public void hello() {
        System.out.println("hello~");
    }
}
​
class Son extends Father{
    public void show() {
        System.out.println("show~");
    }
}

  


 

posted @ 2021-01-31 11:25  奋斗的小范同学  阅读(275)  评论(0编辑  收藏  举报