關(guān)于使用泛型時(shí)靜態(tài)方法為什么要加的原因

問(wèn)題起源
最近我轉(zhuǎn)發(fā)了一John的泛型講解視頻,

看到了評(píng)論區(qū)有一位粉絲關(guān)于靜態(tài)方法泛型使用的疑問(wèn),我當(dāng)時(shí)在評(píng)論區(qū)也解答回復(fù)了,但是如果以后有人也有疑問(wèn)的話,避免重復(fù)回答,所以記錄下來(lái),方便大家查看。

為什么使用靜態(tài)方法時(shí)要在static后面加<T>的原因
根本原因有以下兩點(diǎn):
靜態(tài)方法和普通方法的生命周期不同
靜態(tài)方法生命周期屬于類加載的時(shí)候,在Java中泛型只是一個(gè)占位符,必須傳遞具體類型才可以使用,也就是類實(shí)例化的時(shí)候才傳遞具體參數(shù)類型,由于靜態(tài)方法的加載在類實(shí)例化之前,也就是說(shuō)在類未實(shí)例化的時(shí)候,類中的泛型還沒(méi)有傳遞真正的類型參數(shù),這時(shí)候靜態(tài)方法就已經(jīng)加載完成。顯然,靜態(tài)方法不能使用/也就是訪問(wèn)不到泛型類中的泛型,所以需要加<T>聲明使用哪種泛型類型。
這和靜態(tài)方法不能調(diào)用普通方法/訪問(wèn)普通變量類似,都是因?yàn)殪o態(tài)聲明與非靜態(tài)聲明方法的生命周期不同。
在Java中泛型都會(huì)在編譯器之后被擦除為原始類型
在Java中泛型屬于偽泛型,也就是只在編譯期生效,編譯之后會(huì)進(jìn)行泛型擦除,擦除為最原始的類型,如果是T,最后為Object,如果是<? extends edou>,則擦除為edou類型。
例子
public class Demo<T>{
? ? ?public static T stataicMethod(){...}
? ? ?//上面這個(gè)是編譯會(huì)報(bào)錯(cuò)的;
? ? ?public static<T> T stataicMethod(){...}
? ? // 這個(gè)編譯器可以通過(guò);
}
在上面我們解釋了,Java的泛型在編譯之后會(huì)被擦除,這個(gè)是共識(shí)。
在上面的例子,代碼編譯后T都被會(huì)擦除為原始類型,也就是Object,那為什么static 方法不加<T>會(huì)報(bào)錯(cuò),是因?yàn)榉盒皖怐emo中的泛型參數(shù)的實(shí)例化是在定義對(duì)象的時(shí)候指定的,而靜態(tài)變量和靜態(tài)方法不需要使用對(duì)象來(lái)調(diào)用。對(duì)象都沒(méi)有創(chuàng)建,去調(diào)用沒(méi)有加<T>的靜態(tài)方法,這時(shí)候編譯器無(wú)法確定這個(gè)泛型參數(shù)是何種類型,這時(shí)候就會(huì)編譯報(bào)錯(cuò),所以加<T>表明這是一個(gè)泛型方法,在泛型方法中使用的T是自己在方法中定義的 T,而不是泛型類中的T。
最后
感謝大家對(duì)我的支持,我搬運(yùn)的一些優(yōu)質(zhì)視頻我自己也會(huì)看,覺(jué)得有價(jià)值才會(huì)分享給大家,而不是一味的搬運(yùn),后續(xù)也會(huì)分享我在日常工作中遇到的技術(shù)難題以及如何解決的思路,希望大家多多支持,幫忙點(diǎn)贊。