在Kotlin開發(fā)中如何使用集合詳解
關(guān)于 Kotlin 開發(fā)
使用 Kotlin 開發(fā) Android App 在 Java 工程師群體中變得越來(lái)越流行。如果你由于某些原因錯(cuò)過了 Kotlin,我們強(qiáng)烈建議你看一下這篇文章。
對(duì)于那些處在技術(shù)前沿和喜歡 Kotlin 的開發(fā)者來(lái)說(shuō),本篇文章和他們息息相關(guān)。所以,下面就讓我們來(lái)看一下怎樣在 Kotlin 中使用集合吧。
Kotlin中的集合是基于 Java 集合的框架。本篇文章主要講的是 kotlin.collections 包中的幾個(gè)特性。
數(shù)據(jù)處理
Kotlin 中有一個(gè)拓展函數(shù)的特性,這個(gè)特性可以使 Kotlin 標(biāo)準(zhǔn)庫(kù)(stdlib)支持 JDK 的中的類的方法。舉個(gè)例子:如果你打開Kotlin 標(biāo)準(zhǔn)庫(kù)中的 open_Collection.kt 文件,你可以找到很類似于下面這樣的方法:
/** * Returns a list containing only elements matching the given [predicate]. */ public inline fun <T> Iterable<T>.filter(predicate: (T) -> Boolean): List<T> { return filterTo(ArrayList<T>(), predicate) }
所以,你寫的代碼可能是下面這個(gè)樣子:
val originalList = listOf(1, 2, 3, 4, 5, 6) assertEquals(listOf(2, 4, 6), originalList.filter { it % 2 == 0 }) val originalList = listOf(1, 2, 3, 4, 5, 6, 7, 8, 9, 10) val result = originalList.firstOrNull { it > 4 } assertEquals(result, 5) val originalList = listOf(1, 2, 3, 4, 5, 6, 7, 8, 9, 10) val result = originalList.getOrElse(12) { 12 } assertEquals(result, 12) val originalList = listOf(1, 2, 3, 4, 5, 6, 7, 8, 9, 10) val result = originalList.dropWhile { it < 5 } assertEquals(result, listOf(5, 6, 7, 8, 9, 10)) val originalList = listOf(1, 2, 3, 4, 5, 6, 7, 8, 9, 10) val result = originalList .dropWhile { it < 5 } .find { it < 7 } assertEquals(result, 5)
你需要注意的是:filter和dropWhile 就像其他操作符一樣,返回的是一個(gè)新的事例。這意味著 originalList 不會(huì)改變。
為了更好的理解代碼底層到底發(fā)生了什么,我們打開源碼看一下 listOf() 方法:
/** Returns a new read-only list of given elements. The returned list is serializable (JVM). */ public fun <T> listOf(vararg elements: T): List<T> = if (elements.size > 0) elements.asList() else emptyList()
由于RxJava和 Java 8 的 Stream API 包含類似的方法,所以上面的代碼和 RxJava 以及 Stream API很像。 但是由于 Android 工程師不能使用 Stream API,所以他們更多的使用的 RxJava 處理數(shù)據(jù)的方法來(lái)解決這個(gè)問題。然后,這種操作并不完全正確,原因在于:RxJava 是一個(gè)事件處理庫(kù),而不是數(shù)據(jù)處理。所以你現(xiàn)在可以使用 Kotlin 來(lái)解決這個(gè)問題而不必?fù)?dān)心這些問題。
不可變集合
如果你對(duì)不可變對(duì)象(immutable object)感覺到很陌生的話,我們建議你先看完這個(gè)文檔 看完后,在看一下這個(gè)。
Kotlin區(qū)分可變對(duì)象(mutable object)和不可變對(duì)象(lists, sets, maps等等)的方法和其他編程語(yǔ)言不一樣。在使用Kotlin集合時(shí)準(zhǔn)確區(qū)分這幾種兩種對(duì)象對(duì)于避免不必要的錯(cuò)誤和 bug 都非常有用。
Kotlin允許像 Java 類似的寫法創(chuàng)建 Kotlin 的集合實(shí)例。
val list = ArrayList<String>()
這是最簡(jiǎn)單和整潔的方法. 下面這種方法是最棒的寫法:
val list: kotlin.collections.List<String> = java.util.ArrayList()
我創(chuàng)建了一個(gè)kotlin.collections.List引用,同時(shí)我們也創(chuàng)建了一個(gè)不可變的集合。如果你不是很相信的話,那么我們可以看一下源碼:
public interface List<out E> : Collection<E> { // Query Operations override val size: Int override fun isEmpty(): Boolean override fun contains(element: @UnsafeVariance E): Boolean override fun iterator(): Iterator<E> // Bulk Operations override fun containsAll(elements: Collection<@UnsafeVariance E>): Boolean // Positional Access Operations /** * Returns the element at the specified index in the list. */ public operator fun get(index: Int): E // Search Operations /** * Returns the index of the first occurrence of the specified element in the list, or -1 if the specified * element is not contained in the list. */ public fun indexOf(element: @UnsafeVariance E): Int /** * Returns the index of the last occurrence of the specified element in the list, or -1 if the specified * element is not contained in the list. */ public fun lastIndexOf(element: @UnsafeVariance E): Int // List Iterators /** * Returns a list iterator over the elements in this list (in proper sequence). */ public fun listIterator(): ListIterator<E> /** * Returns a list iterator over the elements in this list (in proper sequence), starting at the specified [index]. */ public fun listIterator(index: Int): ListIterator<E> // View /** * Returns a view of the portion of this list between the specified [fromIndex] (inclusive) and [toIndex] (exclusive). * The returned list is backed by this list, so non-structural changes in the returned list are reflected in this list, and vice-versa. */ public fun subList(fromIndex: Int, toIndex: Int): List<E> }
你看到源碼中沒 add() 方法,也沒有 remove() 方法,同時(shí)也沒有其他的一些方法去改變這個(gè)集合。在這個(gè)例子中,實(shí)例本身是java.util.ArrayList。 下面我們來(lái)通過一個(gè)例子來(lái)解釋為什么:
val list: kotlin.collections.MutableList<String> = java.util.ArrayList() list.add("string")
你最好在本地的源碼中看這例子:
public interface MutableList<E> : List<E>, MutableCollection<E> { // Modification Operations override fun add(element: E): Boolean override fun remove(element: E): Boolean // Bulk Modification Operations override fun addAll(elements: Collection<E>): Boolean /** * Inserts all of the elements in the specified collection [elements] into this list at the specified [index]. * * @return `true` if the list was changed as the result of the operation. */ public fun addAll(index: Int, elements: Collection<E>): Boolean override fun removeAll(elements: Collection<E>): Boolean override fun retainAll(elements: Collection<E>): Boolean override fun clear(): Unit // Positional Access Operations /** * Replaces the element at the specified position in this list with the specified element. * * @return the element previously at the specified position. */ public operator fun set(index: Int, element: E): E /** * Inserts an element into the list at the specified [index]. */ public fun add(index: Int, element: E): Unit /** * Removes an element at the specified [index] from the list. * * @return the element that has been removed. */ public fun removeAt(index: Int): E // List Iterators override fun listIterator(): MutableListIterator<E> override fun listIterator(index: Int): MutableListIterator<E> // View override fun subList(fromIndex: Int, toIndex: Int): MutableList<E> }
怎樣理解:Java 的 ArrayList 是否和 Kotlin 的 List一樣?
val list: kotlin.collections.List<String> = java.util.ArrayList()
實(shí)際上,這里并沒有什么奇怪的地方. Kotlin 的集合繼承了 Java 的 List 的接口。我們可以從 kotlin.collections.Collection.kt 文件中看到:
@file:kotlin.jvm.JvmMultifileClass @file:kotlin.jvm.JvmName("CollectionsKt") package kotlin.collections import kotlin.comparisons.compareValues
正如之前所提的,這個(gè)文件包含了所有的集合擴(kuò)展方法。我們可以看到,我們?cè)?Kotlin 中幾乎可以使用 Java CollectionsKT 類中的所有方法.當(dāng)然,也需要導(dǎo)入 java.util.* 。
讓我們來(lái)看一下我們?cè)?Java 代碼中怎么調(diào)用 Kotlin 集合:
java.util.List<Integer> list = kotlin.collections.CollectionsKt.listOf(3, 4, 5); java.util.List<Integer> filteredList = CollectionsKt.filter(list, item -> item > 4);
你現(xiàn)在可以很清楚的看到 Kotlin 集合是如何使用 Java 的 List 。所有擴(kuò)展函數(shù)都可以作為靜態(tài)方法訪問。
總結(jié)
Android 開發(fā)語(yǔ)言 Kotlin 是一門非常有趣的語(yǔ)言。它能幫助我們編寫更加簡(jiǎn)潔和安全的代碼。初次之外,Kotlin 與 Java 兼容。
好了,以上就是這篇文章的全部?jī)?nèi)容了,希望本文的內(nèi)容對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,如果有疑問大家可以留言交流,謝謝大家對(duì)腳本之家的支持。
相關(guān)文章
android加載系統(tǒng)相冊(cè)圖片并顯示詳解
大家好,本篇文章主要講的是android加載系統(tǒng)相冊(cè)圖片并顯示詳解,感興趣的同學(xué)趕快來(lái)看一看吧,對(duì)你有幫助的話記得收藏一下,方便下次瀏覽2021-12-12android ListView內(nèi)數(shù)據(jù)的動(dòng)態(tài)添加與刪除實(shí)例代碼
ListView內(nèi)數(shù)據(jù)的動(dòng)態(tài)添加與刪除2013-03-03Android UI實(shí)時(shí)預(yù)覽和編寫的各種技巧
大家好,今天給大家分享的是Android中實(shí)時(shí)預(yù)覽UI和編寫UI的各種技巧,2015-11-11Android中關(guān)于相對(duì)布局RelativeLayout的技巧匯總
RelativeLayout是相對(duì)布局控件,以控件之間相對(duì)位置或相對(duì)父容器位置進(jìn)行排列。下面這篇文章主要給大家介紹了關(guān)于Android中相對(duì)布局RelativeLayout的一些技巧,需要的朋友可以參考借鑒,下面來(lái)一起看看吧。2017-02-02android viewpager實(shí)現(xiàn)豎屏滑動(dòng)效果
這篇文章主要為大家詳細(xì)介紹了android viewpager實(shí)現(xiàn)豎屏滑動(dòng)效果,具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下2018-07-07Android自定義View實(shí)現(xiàn)比賽時(shí)間閃動(dòng)效果
這篇文章主要為大家詳細(xì)介紹了Android自定義View實(shí)現(xiàn)比賽時(shí)間閃動(dòng)效果,具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下2018-03-03Android判斷某個(gè)權(quán)限是否開啟的方法
今天小編就為大家分享一篇Android判斷某個(gè)權(quán)限是否開啟的方法,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。一起跟隨小編過來(lái)看看吧2018-07-07Rxjava+Retrofit+Okhttp進(jìn)行網(wǎng)絡(luò)訪問及數(shù)據(jù)解析
這篇文章主要介紹了Rxjava+Retrofit+Okhttp進(jìn)行網(wǎng)絡(luò)訪問及數(shù)據(jù)解析,文章圍繞主題展開詳細(xì)的內(nèi)容介紹,具有一定的參考價(jià)值,感興趣的小伙伴可以參考一下2022-08-08Android中傳值Intent與Bundle的區(qū)別小結(jié)
這篇文章主要給大家總結(jié)介紹了關(guān)于Android中傳值Intent與Bundle的區(qū)別,文中通過示例代碼以及圖文介紹的非常詳細(xì),對(duì)各位Android開發(fā)者們具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面來(lái)一起學(xué)習(xí)學(xué)習(xí)吧2019-03-03