聽說Java泛型很難扔茅?我不信!

作為一個曾被泛型弄得死去活來的小辣雞秸苗,這篇文章將致力于給大家以最清新舒服的方式來把泛型講的清清爽爽~

首先我想以集合來為泛型開個頭召娜,現(xiàn)在咱們這里有一個需求:集合里面有字符串類的數(shù)據(jù),我們要把它打印出來惊楼,代碼很簡單

public class TestDemo {
    public static void main(String[] args) {
        
        
        ArrayList a=new ArrayList();
        a.add("java01");//添加
        a.add("java02");
        a.add("java03");//a:java01,java02,java03
                //a.add(4);//加入一個整形
        Iterator it=a.iterator();
        while(it.hasNext())
        {
            String s=(String)it.next();
            sop(s);
            
        }
    }
    static void sop(Object e) {
        System.out.println(e);
    }
}

一天有一個好事者一不小心加入了一個整形變量玖瘸,編譯沒有問題秸讹,但是在運(yùn)行時會打印錯誤(把上文代碼中的注釋去掉,編譯

java01
java02
java03
Exception in thread "main" java.lang.ClassCastException: java.lang.Integer cannot be cast to java.lang.String
    at TestDemo.main(TestDemo.java:21)

代碼拋了一個異常雅倒,問題在于Integer類型不能強(qiáng)轉(zhuǎn)為String類型

問題來了璃诀,集合作為一個容器對于所有的對象都統(tǒng)統(tǒng)接收,那么我們能不能對容器加以限制蔑匣,比如說劣欢,我們就要String類型的,其他的都統(tǒng)統(tǒng)的不接受裁良?
答案是肯定可以的凿将,主jio登場~(BGM ing.....

泛型

泛型能夠限制傳進(jìn)來的類型
可能說起來有些抽象,我們還是用上面那個例子來說明趴久,見代碼

ArrayList a=new ArrayList();

修改一下

ArrayList<String> a=new ArrayList<String>();

這個時候丸相,我們再試著添加整型4,編譯報(bào)錯

Multiple markers at this line
    - The method add(int, String) in the type ArrayList<String> is not applicable for the arguments 
     (int)
    - Type safety: The method add(Object) belong

意思大概是int類型的不能應(yīng)用類型是String的添加方法

我們已經(jīng)成功的用泛型來限定了傳進(jìn)去的類型了彼棍,在創(chuàng)建對象時<>中傳入合適的類型

問題來了灭忠,使用泛型需要什么條件呢?

我們來看看ArrayList的JDK文檔

Class ArrayList<E>

在ArrayList后面添加了<E>
我們在看看類中的方法

ArrayList中的方法.jpg

比如說add(E e)中參數(shù)的類型和Class ArrayList<E>中的E是一致的

也就是說我們在限定我們創(chuàng)建ArrayList時候的類型參數(shù)和后面方法中的參數(shù)是一致的座硕,這里的E其實(shí)也就是Element的含義
需要注意的是JDK中的Iterator也允許泛型

這里再給出完整的代碼

public class TestDemo {
    public static void main(String[] args) {
        
        
        ArrayList<String> a=new ArrayList<String>();
        a.add("java01");//添加
        a.add("java02");
        a.add("java03");//a:java01,java02,java03
        
        Iterator<String> it=a.iterator();
        while(it.hasNext())
        {
                        //String s-(String)it.next();
            String s=it.next();
            sop(s);
            
        }
    }
    static void sop(Object e) {
        System.out.println(e);
    }
}

這里可以給出兩個添加泛型后的小結(jié)論

1弛作、限定容器中的元素的內(nèi)容
2、避免獲得容器中內(nèi)容的元素時需要強(qiáng)轉(zhuǎn)
這里提出一個問題华匾,是否我們自己能夠使用泛型映琳?
答案是肯定的,接下來給大家介紹常見的情況下使用泛型

類中加泛型

類中所有用到類定義時使用的類型的方法
也就是說蜘拉,方法中傳入的參數(shù)只要和定義類時參數(shù)一致萨西,那么創(chuàng)建對象時就確定了


public class Person<E> {
    void show(E e)
    {
        System.out.println("show-----"+e);
    }
    
}
import javax.print.attribute.standard.MediaSize.Other;

public class TestDemo {
    public static void main(String[] args) {
        Person<String> p=new Person<String>();
        String s="abc";
        p.show(s);
    }
    static void sop(Object e) {
        System.out.println(e);
    }
}

打印一下

show-----abc

Person<E>和show(E e)中的E是同一個E,傳入的類型就被確定了

我想讓方法中使用自己的泛型行不行?也就是方法中的泛型與類無關(guān)
聰明的JAVA會告訴你旭旭,答案肯定也是可以的

方法中添加泛型

格式:修飾符+<E>+返回類型+方法名+參數(shù)
見代碼

//方法中單獨(dú)設(shè)置泛型
public class Person<E> {
    void show(E e)
    {
        System.out.println("show-----"+e);
    }
    public <T> void method(T t)
    {
        System.out.println("method----"+t);
    }
    public static <R> void function(R r)
    {
        System.out.println("function----"+r);
    }
}
public class TestDemo {
    public static void main(String[] args) {
        Person<String> p=new Person<String>();
        String s="abc";
        p.show(s);
        int num=201314;
        p.method(num);
        Person.function(520);
    }
    static void sop(Object e) {
        System.out.println(e);
    }
}

打印一下

show-----abc
method----201314
function----520
又有同學(xué)舉手手說:好像泛型在很多地方都能夠加
答案是肯定的谎脯,接下來我們一起來看還有那些地方能夠加

接口中設(shè)置泛型

格式:interface+接口名+<E>

interface Inter<M>{
    void show(M m);
    <M> void method(M m);
    
}
public class InterTest implements Inter<String>{

    @Override
    public void show(String m) {
        // TODO Auto-generated method stub
        System.out.println("show---"+m);
    }

    @Override
    public <M> void method(M m) {
        // TODO Auto-generated method stub
        System.out.println("method----"+m);
    }

}

到這里了,我們來做一個小總結(jié)

泛型的使用非常廣泛持寄,類源梭、方法、接口都可以使用泛型作為限定類型稍味,其實(shí)它的本質(zhì)就是打破了Object的使用废麻,并且很好的維持了多態(tài)(因?yàn)楸苊饬藦?qiáng)轉(zhuǎn))

好事者又不服,認(rèn)為我們既然利用泛型在創(chuàng)建時限定了類型模庐,那么我現(xiàn)在有一個需求:我有一個Person類烛愧,還有一個Person的子類Student,我想把這兩個類都打印出他們的屬性,我想用一個通用的辦法來打印

這個需求提的很好

泛型限定符

泛型不光支持任何單一類型屑彻,還支持具有繼承關(guān)系的類型
格式:<? extends 類型>允許某一種類型極其子類
那么這里的需求很好的可以滿足

//創(chuàng)建嗎一個基本Person類
public class Person {
    private String name;
    private int age;
    Person(String name,int age)
    {
        this.age=age;
        this.name=name;
    }
    void show()
    {
        System.out.println("person-----"+name+age);
    }
}
//Person類的子類
public class student extends Person {
    private String name;
    private int age;
    private String xuehao;
    student(String name, int age,String xuehao) {
        super(name, age);
        this.xuehao=xuehao;
        // TODO Auto-generated constructor stub
    }
    void show() {
        System.out.println("stu----"+name+age+xuehao);
    }
    
}
//需求:用一種通用的方法打印Person和student類的基本屬性
public class TestDemo {
    public static void main(String[] args) {
        ArrayList<Person> per_al=new ArrayList<Person>();
        per_al.add(new Person("xiaoming01",14));
        per_al.add(new Person("xiaoming02",12));
        per_al.add(new Person("xiaoming03",13));
        per_al.add(new Person("xiaoming04",42));
        per_al.add(new Person("xiaoming05",16));
        ArrayList<student> stu_al=new ArrayList<student>();
        stu_al.add(new student("xiaoming01",14,"201514160101"));
        stu_al.add(new student("xiaoming02",14,"201514160102"));
        stu_al.add(new student("xiaoming03",14,"201514160103"));
        stu_al.add(new student("xiaoming04",14,"201514160104"));
        printColl(per_al);
        printColl(stu_al);
    }
    public static void printColl(ArrayList<? extends Person> al)
    {
        Iterator<? extends Person> it=al.iterator();
        while(it.hasNext())
            it.next().show();
    }
    static void sop(Object e) {
        System.out.println(e);
    }
}

打印一下

person-----xiaoming0114
person-----xiaoming0212
person-----xiaoming0313
person-----xiaoming0442
person-----xiaoming0516
stu----null0201514160101
stu----null0201514160102
stu----null0201514160103
stu----null0201514160104

這樣子佛寿,Iterator中的泛型的類型就允許接收Person和Person的子類

我們不光可以接收類及其子類艰猬,我們還可以接收類及其父類

格式:<? super student>

總結(jié)

在創(chuàng)建類威彰、方法纺铭、接口的時候利用了泛型限定符,我們可以定義單類型搏恤,類以及其父類违寿,類以及子類三種形式

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末,一起剝皮案震驚了整個濱河市熟空,隨后出現(xiàn)的幾起案子藤巢,更是在濱河造成了極大的恐慌,老刑警劉巖息罗,帶你破解...
    沈念sama閱讀 222,000評論 6 515
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件掂咒,死亡現(xiàn)場離奇詭異,居然都是意外死亡迈喉,警方通過查閱死者的電腦和手機(jī)绍刮,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 94,745評論 3 399
  • 文/潘曉璐 我一進(jìn)店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來挨摸,“玉大人孩革,你說我怎么就攤上這事〉迷耍” “怎么了膝蜈?”我有些...
    開封第一講書人閱讀 168,561評論 0 360
  • 文/不壞的土叔 我叫張陵,是天一觀的道長熔掺。 經(jīng)常有香客問我饱搏,道長,這世上最難降的妖魔是什么置逻? 我笑而不...
    開封第一講書人閱讀 59,782評論 1 298
  • 正文 為了忘掉前任窍帝,我火速辦了婚禮,結(jié)果婚禮上诽偷,老公的妹妹穿的比我還像新娘。我一直安慰自己疯坤,他們只是感情好报慕,可當(dāng)我...
    茶點(diǎn)故事閱讀 68,798評論 6 397
  • 文/花漫 我一把揭開白布。 她就那樣靜靜地躺著压怠,像睡著了一般眠冈。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上,一...
    開封第一講書人閱讀 52,394評論 1 310
  • 那天蜗顽,我揣著相機(jī)與錄音布卡,去河邊找鬼。 笑死雇盖,一個胖子當(dāng)著我的面吹牛忿等,可吹牛的內(nèi)容都是我干的。 我是一名探鬼主播崔挖,決...
    沈念sama閱讀 40,952評論 3 421
  • 文/蒼蘭香墨 我猛地睜開眼贸街,長吁一口氣:“原來是場噩夢啊……” “哼!你這毒婦竟也來了狸相?” 一聲冷哼從身側(cè)響起薛匪,我...
    開封第一講書人閱讀 39,852評論 0 276
  • 序言:老撾萬榮一對情侶失蹤,失蹤者是張志新(化名)和其女友劉穎脓鹃,沒想到半個月后逸尖,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體,經(jīng)...
    沈念sama閱讀 46,409評論 1 318
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡瘸右,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 38,483評論 3 341
  • 正文 我和宋清朗相戀三年娇跟,在試婚紗的時候發(fā)現(xiàn)自己被綠了。 大學(xué)時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片尊浓。...
    茶點(diǎn)故事閱讀 40,615評論 1 352
  • 序言:一個原本活蹦亂跳的男人離奇死亡逞频,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出栋齿,到底是詐尸還是另有隱情苗胀,我是刑警寧澤,帶...
    沈念sama閱讀 36,303評論 5 350
  • 正文 年R本政府宣布瓦堵,位于F島的核電站基协,受9級特大地震影響,放射性物質(zhì)發(fā)生泄漏菇用。R本人自食惡果不足惜澜驮,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,979評論 3 334
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望惋鸥。 院中可真熱鬧杂穷,春花似錦、人聲如沸卦绣。這莊子的主人今日做“春日...
    開封第一講書人閱讀 32,470評論 0 24
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽滤港。三九已至廊蜒,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間,已是汗流浹背山叮。 一陣腳步聲響...
    開封第一講書人閱讀 33,571評論 1 272
  • 我被黑心中介騙來泰國打工著榴, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留,地道東北人屁倔。 一個月前我還...
    沈念sama閱讀 49,041評論 3 377
  • 正文 我出身青樓脑又,卻偏偏與公主長得像,于是被迫代替她去往敵國和親汰现。 傳聞我的和親對象是個殘疾皇子挂谍,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 45,630評論 2 359