-
java泛型
-
什么是泛型? 泛指一切類型
常使用 T R V K I O 表示
-
協(xié)變與形變
class MyClass { public static void main(String[] args) { List<Object> a = new ArrayList(); List<String> b = new ArrayList(); a = b; // 報(bào)錯(cuò),為什么,a 需要 List<Objects>類型,而b 為List<String>類型 ***************** // 此時(shí)需要使用協(xié)變 父類接收子類 協(xié)變 ? extends List<? extends Object> c = new ArrayList(); // ? 為占位符,表示一個(gè)繼承于Object的子類 List<String> d = new ArrayList(); c = d;// 正確!!! ***************** List<Object> e = new ArrayList(); List<String> f = new ArrayList(); f = e;// 報(bào)錯(cuò),f需要List<Object>類型,而e為List<String>類型,類型不匹配 ***************** // 此時(shí)需要使用形變 子類接收父類 形變 ? super List<Object> g = new ArrayList(); List<? super String> h = new ArrayList(); h = g;// 正確! } } -
java泛型類的使用
注意:泛型類中的方法只是使用了泛型類類型作為參數(shù)的函數(shù),不是泛型函數(shù)
// 泛型類 // T type class Bag<T> { private T value; public void setValue(T value) { this.value = value; } public T getValue { return this.value; } // main public static void main(String[] args) { // 前面<> 和 后面<> 必須指定一處類型 Bag<String> schoolBag = new Bag<>(); schoolBag.setValue("語文書"); System.out.println(schoolBag.getValue()); } }
-
-
kotlin泛型類的使用
-
kotlin泛型類的使用
kotlin: out 這個(gè)類型只能作為返回值 輸出 生產(chǎn)
kotln: in只能作為參數(shù) 接受 消費(fèi)
class Bag<in I,out O>(var value: @UnsafeVariance I,var result: @UnsafeVariance O) { fun setValue(v1: I) { value = v1 } fun getValue(): O { return result } }
-
-
Kotlin泛型函數(shù)的使用
何為泛型函數(shù)?不確定參數(shù)或者返回值類型的函數(shù)就是泛型函數(shù)
-
僅有一個(gè)泛型
fun <T> test() {} fun <T> test1(): T {} fun <T> test2(v1: T) {} -
放回值和參數(shù)類型均需要自己指定
fun <T,R> test(v1: T, v2: T): R? { return null }
-
-
Kotlin高階函數(shù)分析
-
何為高階函數(shù)與為什么需要使用inline?
高階函數(shù)是將函數(shù)用作參數(shù)或返回值的函數(shù),實(shí)際開發(fā)過程中一般所有高階函數(shù)都必須使用inline修飾,使之成為內(nèi)聯(lián)函數(shù)。不使用inline修飾高階函數(shù)時(shí),使用此類高階函數(shù)會(huì)帶來一些運(yùn)行時(shí)的效率損失,因?yàn)榫幾g時(shí),每一個(gè)函數(shù)都是一個(gè)對(duì)象,內(nèi)存分配(對(duì)于函數(shù)對(duì)象和類)和虛擬調(diào)用會(huì)引入運(yùn)行時(shí)間開銷,降低效率。當(dāng)inline修飾了高階函數(shù)時(shí),此時(shí)編譯時(shí)程序只是做了一個(gè)展開/替換(類似于C語言的宏定義),所以在許多情況下我們通過使用inline內(nèi)聯(lián)化 lambda 表達(dá)式來消除這類的開銷。
-
lambda表達(dá)式分析
inline fun String.show1(lambda: (String) -> Unit) { // lamba表達(dá)式為String類型的形參,沒有返回值 // lambda 表達(dá)式里面是 it lambda(this) } inline fun String.show2(lambda: String.() -> Unit ) { // lambda 表達(dá)式里面是 this this.lambda() } fun main() { "jack".show1{ println("hello $it") } "Merry".show2{ println("hello $this") } } -
lambda與泛型的綜合運(yùn)用
- 給任意一個(gè)類型添加一個(gè)擴(kuò)展函數(shù),lambda中使用it訪問這個(gè)對(duì)象
fun <T> T.show1(lambda: (T) -> Unit) { lambda(this) // 在這個(gè)函數(shù)中this指代的是調(diào)用這個(gè)擴(kuò)展函數(shù)類型為T的對(duì)象,并把它作為參數(shù)傳遞給lambda, // 在lambda中使用it訪問這個(gè)對(duì)象 }- 給任意一個(gè)類型添加一個(gè)擴(kuò)展函數(shù),lambda中使用this訪問這個(gè)對(duì)象
fun <T> T.show2(lambda: T.() -> Unit) { this.lambda() // this指代是調(diào)用這個(gè)擴(kuò)展函數(shù)類型為T的對(duì)象,再將其作為調(diào)用lambda的對(duì)象 // 在lambda中使用this訪問這個(gè)對(duì)象 }- 給任意一個(gè)類型添加一個(gè)擴(kuò)展函數(shù),并將這個(gè)對(duì)象傳遞給lambda表達(dá)式,lambda返回值的類型由lambda最后一行的結(jié)果決定
fun <T,R> T.show3(lambda: (T) -> R) { val result = lambda(this) println(result!!::class.java.name) // 上行可以打印出lambda表達(dá)式最后一行結(jié)果的值 }
-
運(yùn)行效果如下
屏幕截圖 2022-05-29 172914.png屏幕截圖 2022-05-29 173046.png
-
-
Kotlin語法糖分析
-
apply分析
apply作用:使用apply可以進(jìn)行初始化操作
inline fun <T> T.myApply(lambda: T.() -> T): T { this.lambda() return this } -
also分析
also作用:使用also可以完成同時(shí)性的操作
inline fun <T> T.myAlso(lambda: (T) -> T): T { lambda(this) return this } -
run分析
run作用:使用run可以執(zhí)行一段代碼
inline fun <R> myRun(lambda: () -> R): R { return lambda() } inline fun <T,R> T.myRun(lambda: T.() -> R): R { return this.lambda() } -
with分析
inline fun <T,R> myWith(value: T,lambda: T.() -> R): R { return value.lambda() } -
forEach分析
forEach作用:使用forEach可以遍歷完成相關(guān)的操作
inline fun <T> Iterable<T>.myForEach(lambda: (T) -> Unit): Unit { for (item in this) { lambda(item) } }
-

