02. 程式設計核心內功心法之泛型

柒徳嚨咚嗆發表於2020-12-27

泛型

public static void main(String[] args) {
    //List list = new ArrayList();
    //指定能夠存放的資料型別,統一型別防止出現 型別轉換異常
    List<String> list = new ArrayList();
    list.add(1);
    list.add("hello");
    list.add(new Object());
    for (Object obj:list) {
        System.out.println((String)obj); //java.lang.ClassCastException
    }
}

本質:引數化型別

泛型的擦除

泛型只在編譯階段有效,編譯之後JVM會採取去泛型化的措施.

泛型在執行階段是沒有效果

public static void main(String[] args) throws Exception {
    List<String> list = new ArrayList();
    list.add("1");
    list.add("hello");
    list.add("2");
    for (Object obj:list) {
        System.out.println((String)obj);
    }
    //反射賦值
    Class<? extends List> aClass = list.getClass();
    Method method = aClass.getDeclaredMethod("add", Object.class);
    method.invoke(list,new Object());
    System.out.println(list);//沒有任何問題
}

一、泛型萬用字元介紹

1、無邊界萬用字元

public static void main(String[] args) {
    List<String> list1 = new ArrayList<>();
    list1.add("gupao");
    list1.add("bobo");
    list1.add("mic");
    loop(list1);
}
/**
 * < ? > 通用的型別可以是任意型別
 */
public static void loop(List<?> list){
    for (int i = 0; i < list.size() ; i++) {
        System.out.println(list.get(i));
    }
}

2、上邊界萬用字元

public static void main(String[] args) {
    List<String> list1 = new ArrayList<>();
    list1.add("gupao");
    list1.add("bobo");
    list1.add("mic");
    // loop(list1);
    List<Number> list2 = new ArrayList<>();
    list2.add(1);
    list2.add(2);
    list2.add(3);
}
/**
 *  < ? extends Number >
 *  通用的型別必須是Number及其子類
 * @param list
 */
public static void loop(List<? extends Number> list){
    for (int i = 0; i < list.size() ; i++) {
        System.out.println(list.get(i));
    }
}

3、下邊界萬用字元

public static void main(String[] args) {
    List<String> list1 = new ArrayList<>();
    list1.add("gupao");
    list1.add("bobo");
    list1.add("mic");
    loop(list1);
    List<Number> list2 = new ArrayList<>();
    list2.add(1);
    list2.add(2);
    list2.add(3);
    loop(list2);
}
/**
 * < ?  super Number >
 * 通用型別必須是Number 到Object型別的物件
 * @param list
 */
public static void loop(List<? super Number> list){
    for (int i = 0; i < list.size() ; i++) {
        System.out.println(list.get(i));
    }
}

二、泛型的具體使用

規則: 必須先宣告再使用

1、泛型的宣告是通過"<>"實現

2、約定泛型可以使用單個大寫字母來表示 K E T V 等

/**
 * 泛型沒有宣告就直接使用了
 * @param t
 * @return
 */
public <T> T func(T t){
    return null;
}

1、泛型類

public class Fun <T>{

    private T t;

    public T getT() {
        return t;
    }

    public void setT(T t) {
        this.t = t;
    }

    public Fun(T t) {
        this.t = t;
    }
}

//PersonBean
public class PersonBean {
    private int id;
    private String name;
    private String password;
    //get/set
}
//測試
public static void main(String[] args) {

    PersonBean bean = new PersonBean();
    bean.setId(1);
    bean.setName("Andy");
    bean.setPassword("12345");

    Fun<PersonBean> pn = new Fun(bean); //PersonBean
    Fun<String> s = new Fun("hello");   //String
}

增加了程式碼的靈活度

2、泛型方法

public class Fun <K,V>{

    //普通方法 可以使用 類中定義的泛型
    public K method1(K k,V v){
        return (K)null;
    }

    //普通方法  使用方法中定義的泛型
    public <T> T method2(T t,V v){
        return (T)null;
    }

    //在靜態方法中我們沒法使用 類中定義的泛型,想使用需自己定義<k>
    public static <K> K method3(){
        return null;
    }
}

3、泛型介面

public interface CalGeneric <T> {

    T add(T a,T b);

    T sub(T a,T b);

    T mul(T a,T b);

    T div(T a,T b);
}

//實現類 - Integer
public class CalIntegerGeneric implements  CalGeneric<Integer> {
    @Override
    public Integer add(Integer a, Integer b) {
        return null;
    }

    @Override
    public Integer sub(Integer a, Integer b) {
        return null;
    }

    @Override
    public Integer mul(Integer a, Integer b) {
        return null;
    }

    @Override
    public Integer div(Integer a, Integer b) {
        return null;
    }
}
//實現類 - Double
public class CalDoubleGeneric implements CalGeneric<Double>{
    @Override
    public Double add(Double a, Double b) {
        return null;
    }

    @Override
    public Double sub(Double a, Double b) {
        return null;
    }

    @Override
    public Double mul(Double a, Double b) {
        return null;
    }

    @Override
    public Double div(Double a, Double b) {
        return null;
    }
}

相關文章