Kotlin中空判斷處理操作實例
Kotlin中的一個偉大創(chuàng)前舉就是空指針的處理,在代碼的編譯階段就能檢測可能出現(xiàn)的空指針問題,示例代碼如下:
data class Person(var name: String? = null)
fun sayHello(name: String) {
println("Hello $name")
}
fun main() {
val person = Person("Even")
if (person.name != null) {
sayHello(person.name)
}
}
在IntelliJ中,如上代碼會報錯,如下:

提示的錯誤信息翻譯為:智能強制轉(zhuǎn)換為’String’是不可能的,因為’person.name’是一個可變屬性,此時可能已經(jīng)被更改了。
要想編譯通過,需要這樣做:
sayHello(person.name!!)
哎?我記得學Kotlin的時候有解釋說如果已經(jīng)判斷了不是空了的話,就不需要添加 !! 符號的,為什么這里不添加的話會報錯呢?其實原因就是報錯信息上提示的,因為name是用var修飾的,而且這是一個成員變量,雖然你做了非空的判斷,但是判斷之后,這個成員屬性有可能在其它線程被修改了,比如在其他線程設置為null了,所以,這樣的話就會出現(xiàn)空指針異常了,所以添加 !! 符號來解決報錯不是最佳實踐,在我這個示例中,我們知道沒有開多線程去修改person的name屬性,所以可以加 !! 來解決,但是最好不要這樣做,如果我們知道name屬性不會被修改,則可以使用val修飾,如下:

可以看到,此時不需要添加 !! 也不報錯了,因為IDE知道name是一個不可變屬性,判斷了不是空之后,就永遠不可能是空了。
有時候,name屬性就需要發(fā)生變化,就必須聲明為var,此時怎么解決呢?,可以通過添加局部變量解決,如下:

如上代碼,IDE沒有報錯。我們通過添加一個val類型的name局部變量來保存person.name的值,這樣的話,判斷了name為不為空之后,即使person.name在子線程被設置為空了,但是局部變量name不會受到影響。我們在閱讀一些系統(tǒng)源碼的時候,不論是Java源碼或是Kotlin的源碼,經(jīng)常發(fā)現(xiàn)別人在判斷一個對象的屬性的可空性的時候,都是先聲明一個局部變量保存該對象屬性再來判斷,不懂事的時候就會奇怪別人為什么要多此一舉,現(xiàn)在明白了,別人是為了預防直接判斷對象屬性出現(xiàn)的多線程修改帶來的問題。
添加局部變量的話,即使是var類型的局部變量IDE也能判斷是否為空,示例如下:

如上代碼,可以看到,局部變量name是可變類型的,但是也不需要添加 !! 符號,因為var類型的局部變量不會被子線程修改,所以判斷了不為空之后就不會為空。最后賦值了”Lily“,然后傳給sayHello(name),這里并沒有做非空判斷啊,sayHello接受的是不可空的String,但是name是一個可空String啊,道理也很簡單,因為這是局部變量,沒有子線程的干擾,IDE能檢測到name在傳給sayHello之前是賦值了”Lily"的,之后沒有再賦值為null也是能檢測出來的,所以這里不需要做可空判斷也能編譯通過。如果沒有賦值“Lily",則IDE就不知道name是否為空了,就會報錯,如下:

或者,如果我們使用的是一個成員變量,即使前一句代碼賦值了下一句就用也是會報錯的,原因就是它有可能在子線程被設置為null了,如下:

所以,Kotlin是真的很強,如果你在使用一個變量,只要IDE沒報錯,你就可以放心的使用,不需要做空判斷,你可以放心,運行時不會有空指針問題的。如果IDE報錯了,就是有可能發(fā)生空指針的,此時你就不要強制添加 !! 來逃避問題了,一定要做合理的空指針判斷處理。如果你使用Java的話,要不要做空指針處理IDE是沒有提示的,你只能自己用腦子去想要不要做空指針判斷處理,事實往往是我們根本就不去想要不要做處理,或者即使思考過了,也會有思考出錯的時候,比如可能出現(xiàn)空指針的地方,但是你寫代碼時你認為不會出現(xiàn)空指針,所以你沒做非空判斷處理,則運行時就有可能出現(xiàn)空指針異常了。而Kotlin就會有提示,只要IDE沒報錯就不用做空指針處理,只要IDE報錯了就要做空指針處理,這真是爽歪歪啊,你不需要去思考什么時候應該添加空指針判斷處理了!
注:這個可空判斷也適用于類型智能轉(zhuǎn)換,這個知識點在官網(wǎng)教程上也找到了答案:https://kotlinlang.org/docs/typecasts.html#unsafe-cast-operator,相關內(nèi)容如下:
Note that smart casts work only when the compiler can guarantee that the variable won’t change between the check and the usage. More specifically, smart casts can be used under the following conditions:
val local variables - always, with the exception of local delegated properties.
val properties - if the property is private or internal or if the check is performed in the same module where the property is declared. Smart casts cannot be used on open properties or properties that have custom getters.
var local variables - if the variable is not modified between the check and the usage, is not captured in a lambda that modifies it, and is not a local delegated property.
var properties - never, because the variable can be modified at any time by other code.
附:?.和!!.
其實kotlin是非常人性話的,你定義了一個可為空的變量但是你依然可以去操作的。我們修改一下上面的寫法:
val a:String = "我加小明" val b:String ?= null val c:String? = "我加小明" ? println(a.length) ? println(b?.length) ? ?println(c!!.length)
這樣編譯就通過。
這里的**?.**就是相當于Java的如果為空就返回null 而kotlin強制讓我們?nèi)ヌ幚?,這樣就避免了很多空指針異常
if(b==null) return null;
當然如果你不想直接為null,你說當為空時我想自己去處理,kotlin還有語法**?:**
val b:String ?= null println(b?.length?:"我錯了")
!!. 表示我任性,告訴編譯器不要去做非空檢查,為空就拋異常
總結(jié)
到此這篇關于Kotlin中空判斷處理操作的文章就介紹到這了,更多相關Kotlin空判斷處理內(nèi)容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關文章希望大家以后多多支持腳本之家!
相關文章
解決ViewPager和SlidingPaneLayout的滑動事件沖突問題
下面小編就為大家分享一篇解決ViewPager和SlidingPaneLayout的滑動事件沖突問題,具有很好的參考價值,希望對大家有所幫助。一起跟隨小編過來看看吧2018-01-01
Android?PowerManagerService?打開省電模式
這篇文章主要介紹了Android?PowerManagerService打開省電模式,文章通告省電模式的打開過程、什么是?battery?saver?sticky?模式兩部分展開詳情,感興趣的朋友可以參考一下2022-08-08
Android Flutter基于WebSocket實現(xiàn)即時通訊功能
WebSocket是一種在單個TCP連接上進行全雙工通信的協(xié)議。本文將利用Flutter WebSocket實現(xiàn)即時通訊功能,文中示例代碼講解詳細,感興趣的可以了解一下2022-03-03
Android6.0 storage目錄sd卡存儲的路徑創(chuàng)建詳解
這篇文章主要介紹了Android6.0 storage目錄sd卡存儲的路徑創(chuàng)建的相關資料,需要的朋友可以參考下2017-01-01
android使用SharedPreferences進行數(shù)據(jù)存儲
Android平臺給我們提供了一個SharedPreferences類,它是一個輕量級的存儲類,特別適合用于保存軟件配置參數(shù)。有興趣的可以了解一下。2017-02-02
Android 6.0以上權限拒絕打開權限設置界面的解決方法
今天小編就為大家分享一篇Android 6.0以上權限拒絕打開權限設置界面的解決方法,具有很好的參考價值,希望對大家有所幫助。一起跟隨小編過來看看吧2018-07-07

