最新国产好看的视频,伊人天堂AV在线,国产Aaaaaa视频,蜜臀视频在线观看一区,人妻av色图,密臀久久久精品影片,青青视频免费观看毛片,久草在线观看视,国产三级精品色情在线

Kotlin淺析延遲初始化與密封類的實現(xiàn)方法

 更新時間:2022年08月02日 14:43:59   作者:m0_63970488  
Kotlin語言的許多特性,包括變量不可變,變量不可為空,等等。這些特性都是為了盡可能地保證程序安全而設計的,但是有些時候這些特性也會在編碼時給我們帶來不少的麻煩,下面我們來了解延遲初始化和密封類的特點

一、lateinit延遲初始化關鍵字

Kotlin中很多語法特性,如變量不可變,變量不可為空,等等 這些特性都是為了盡可能地保證程序安全而設計的,比如你的類中存在很多全局變量實例,為了保證它們的能夠滿足Kotlin的空指針檢查語句標準,你不得不做非空判斷保護,即使你非常確定它們不會為空。

下面距離看一下 :

class MainActivity : AppCompatActivity() {
    private var s: String? = null
    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContentView(R.layout.activity_main)
        s = "test"
        Log.d("TAG", "onCreate: ${s!!.length}")
    }
}

我們將s 設置為了全局變量 , 但是它的賦值工作在onCreate()方法進行的,因此不得不將s賦值為null。

雖然你確定在打印前已經(jīng)將s賦值成功,但是打印s的長度仍然要進行判空處理才行,否則編譯不通過。

當你的代碼中越來越多的全局變量實例時,這個問題就會變得越來越明顯,到時候可能必須寫大量額外判空處理的代碼,卻只是為了滿足Kotlin的編譯要求。

幸運的是,這個問題有解決辦法的且非常之簡單,就是對全局變量進行延遲初始化。

初始化使用的關鍵字 lateinit ,它可以高速編譯器,我會在晚些時候?qū)@個變量進行初始化,這樣就不用一開始就賦值為null了。

class MainActivity : AppCompatActivity() {
    private lateinit var s: String
    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContentView(R.layout.activity_main)
        s = "test"
        Log.d("TAG", "onCreate: ${s.length}")
    }
}

可以看到,加上了lateinit關鍵字 ,這樣一開始就不用賦值為null了,打印長度的時候也不用進行判空處理了,當然使用lateinit關鍵字 也不是沒有風險,如果沒有進行賦值,那么程序一定會崩潰,并拋出異常。

另外,我們可以通過代碼來判斷全局變量是否已完成了初始化工作,這樣某些時候可以有效避免重復對某一個變量進行初始化操作。

class MainActivity : AppCompatActivity() {
    private lateinit var s: String
    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContentView(R.layout.activity_main)
        if (!::s.isInitialized) {
            s = "test"
        }
        Log.d("TAG", "onCreate: ${s.length}")
    }
}

二、使用密封類優(yōu)化代碼

新建一個Kotlin文件,代碼如下 :

interface Result
class Success(val msg: String) : Result
class Failure(val error: Exception) : Result

這里定義了一個Result接口,用于表示某個操作的執(zhí)行結(jié)果,接口中沒有編寫任何內(nèi)容。然后定義了兩個類去實現(xiàn)Result接口:一個Success類用于表示成功時結(jié)果,一個Failure類用于表示失敗時結(jié)果。

接下來再定義一個getResultMsg()方法 ,用于獲取最后執(zhí)行結(jié)果的信息,代碼如下:

fun getResultMsg(result: Result) = when (result) {
    is Success -> result.msg
    is Failure -> result.error.message
    else -> throw IllegalArgumentException()
}

getResultMsg()方法中接受一個Result參數(shù),我們通過when語句來判斷,如果Result屬于Success就返回成功的消息,如果Result是Failure就返回錯誤的信息,到目前為止代碼是沒什么問題的,煩人的是不得不寫一個else條件語句,否則Kotlin編譯不通過,其實代碼永遠也走不到else里 因為只有兩種類型的存在,只是為了滿足Kotlin的語法而已。

另外,編寫else條件還有一個潛在的風險,如果我們新增一個Unknown類并實現(xiàn)了Result接口,用于表示未知的執(zhí)行結(jié)果,但是忘記了在getResultMsg()方法中添加相應的條件,編譯器不會提醒我們的,而是直接進入else條件里面去,從里面拋出異常并導致程序崩潰。

Kotlin的密封類很好的解決了此問題,密封類的關鍵字是sealed class ,它的用法同樣很簡單,我們可以輕松的將Result接口改造成密封類寫法:

sealed class Result
class Success(val msg: String) : Result()
class Failure(val error: Exception) : Result()
fun getResultMsg(result: Result) = when (result) {
    is Success -> result.msg
    is Failure -> result.error.message
}

代碼沒什么變化,只是將interface改成了 sealed class。密封類是一個可繼承的類,因此在繼承它的時候還需要加上一對括號。

密封類的優(yōu)點是,可以再getResultMsg() 方法中取消else條件語句。

為什么取消掉else條件語句還能編譯通過呢,Kotlin編譯器會自動檢查該密封類有哪些子類,并強制要求將每一個子類所對應的條件全部處理。這樣就可以保證,即使沒有else條件,也不可能出現(xiàn)漏寫的情況,如果現(xiàn)在新增一個Unknown類,并也讓它繼承自Result,此時getResultMsg()方法就一定會報錯,必須添加Unknown語句條件才能編譯通過。

注意:密封類及其所有子類只能定義同一個文件的頂層位置,不能嵌套在其他類中,這也是被密封類底層實現(xiàn)機制所限制的。

到此這篇關于Kotlin淺析延遲初始化與密封類的實現(xiàn)方法的文章就介紹到這了,更多相關Kotlin延遲初始化內(nèi)容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關文章希望大家以后多多支持腳本之家!

相關文章

  • Android仿ios加載loading菊花圖效果

    Android仿ios加載loading菊花圖效果

    這篇文章主要介紹了Android仿ios加載loading菊花圖效果,本文通過實例代碼效果圖展示給大家介紹的非常詳細,具有一定的參考借鑒價值,需要的朋友可以參考下
    2018-09-09
  • Android圖片加載框架Gilde源碼層深入分析

    Android圖片加載框架Gilde源碼層深入分析

    Glide就像Picasso,可以從多個源去加載和顯示圖片,同時也兼顧緩存和在做圖片處理的時候維持一個低內(nèi)存消耗。它已經(jīng)在Google官方APP中使用了,就和Picasso一樣受歡迎
    2022-11-11
  • Android Studio簽名打包的兩種方式(圖文教程)

    Android Studio簽名打包的兩種方式(圖文教程)

    這篇文章主要介紹了Android Studio簽名打包的兩種方式(圖文教程),文中通過示例代碼介紹的非常詳細,對大家的學習或者工作具有一定的參考學習價值,需要的朋友們下面隨著小編來一起學習學習吧
    2020-10-10
  • Android Jetpack組件庫LiveData源碼深入探究

    Android Jetpack組件庫LiveData源碼深入探究

    LiveData是Jetpack組件的一部分,更多的時候是搭配ViewModel來使用,相對于Observable,LiveData的最大優(yōu)勢是其具有生命感知的,換句話說,LiveData可以保證只有在組件( Activity、Fragment、Service)處于活動生命周期狀態(tài)的時候才會更新數(shù)據(jù)
    2022-09-09
  • Android編程之簡單逐幀動畫Frame的實現(xiàn)方法

    Android編程之簡單逐幀動畫Frame的實現(xiàn)方法

    這篇文章主要介紹了Android編程之簡單逐幀動畫Frame的實現(xiàn)方法,結(jié)合實例較為詳細的分析了Android逐幀動畫的原理、步驟與具體實現(xiàn)技巧,需要的朋友可以參考下
    2015-12-12
  • Flutter應用框架運行微信小程序方法

    Flutter應用框架運行微信小程序方法

    這篇文章主要介紹了在Flutter?App內(nèi)運行微信小程序的過程,文中通過示例代碼介紹的非常詳細,對大家的學習或者工作具有一定的參考學習價值,需要的朋友們下面隨著小編來一起學習吧
    2023-02-02
  • android中view手勢滑動沖突的解決方法

    android中view手勢滑動沖突的解決方法

    本篇文章主要介紹了android中view手勢滑動沖突的解決方法,主要解決方法有兩種,外部和內(nèi)部攔截。有需要的可以參考下。
    2016-11-11
  • Android實現(xiàn)滾動刻度尺效果

    Android實現(xiàn)滾動刻度尺效果

    本篇文章主要介紹了Android實現(xiàn)滾動刻度尺效果,小編覺得挺不錯的,現(xiàn)在分享給大家,也給大家做個參考。一起跟隨小編過來看看吧
    2017-05-05
  • 詳解Android JNI的基本使用(CMake)

    詳解Android JNI的基本使用(CMake)

    本文介紹了Android JNI的基本使用(CMake),小編覺得挺不錯的,現(xiàn)在分享給大家,也給大家做個參考。一起跟隨小編過來看看吧
    2017-12-12
  • 詳解Android平臺JSON預覽(JSON-handle)

    詳解Android平臺JSON預覽(JSON-handle)

    這篇文章主要介紹了Android平臺JSON預覽(JSON-handle),小編覺得挺不錯的,現(xiàn)在分享給大家,也給大家做個參考。一起跟隨小編過來看看吧
    2018-09-09

最新評論

辽阳市| 周至县| 南澳县| 葫芦岛市| 丰台区| 大竹县| 丰都县| 泸溪县| 葫芦岛市| 洛宁县| 潼南县| 上栗县| 南平市| 陈巴尔虎旗| 始兴县| 济南市| 肇东市| 寿阳县| 土默特右旗| 新昌县| 长垣县| 兴文县| 宁陵县| 万全县| 洪洞县| 体育| 临江市| 承德县| 海阳市| 皋兰县| 鹤庆县| 平乐县| 莎车县| 明溪县| 桃园市| 柘城县| 化州市| 延安市| 余干县| 潢川县| 微山县|