<ruby id="bdb3f"></ruby>

    <p id="bdb3f"><cite id="bdb3f"></cite></p>

      <p id="bdb3f"><cite id="bdb3f"><th id="bdb3f"></th></cite></p><p id="bdb3f"></p>
        <p id="bdb3f"><cite id="bdb3f"></cite></p>

          <pre id="bdb3f"></pre>
          <pre id="bdb3f"><del id="bdb3f"><thead id="bdb3f"></thead></del></pre>

          <ruby id="bdb3f"><mark id="bdb3f"></mark></ruby><ruby id="bdb3f"></ruby>
          <pre id="bdb3f"><pre id="bdb3f"><mark id="bdb3f"></mark></pre></pre><output id="bdb3f"></output><p id="bdb3f"></p><p id="bdb3f"></p>

          <pre id="bdb3f"><del id="bdb3f"><progress id="bdb3f"></progress></del></pre>

                <ruby id="bdb3f"></ruby>

                ??碼云GVP開源項目 12k star Uniapp+ElementUI 功能強大 支持多語言、二開方便! 廣告
                ## 協程的取消需要內部配合 單純的執行`job.cancel()`是無法取消當前執行的協程,就像無法取消正在執行過程中的線程; ```kotlin fun main() = runBlocking { val job = launch(Dispatchers.Default) { var i = 0 // 變化在這里,只有協程處于活躍狀態的時候,才會繼續執行循環內部的代碼 while (isActive) { Thread.sleep(500L) i++ println("i = $i") } } delay(2000L) job.cancel() job.join() println("End") } ``` ## 不要輕易打破協程的父子結構 下面代碼中`firstJob`無法通過`parentJob.cancel`被取消,因為`firstJob`設置了自己的`Job()`對象,并沒有關聯`parentJob`,打破了其協程的父子結構; ```kotlin fun main2() = runBlocking { val parentJob = launch(Dispatchers.IO) { val firstJob = launch(Job()) { var i = 0 while (isActive) { Thread.sleep(500L) i++ println("First i = ${i}") } } val secondJob = launch { var i = 0 while (isActive) { Thread.sleep(500L) i++ println("Second i = ${i}") } } } delay(2000L) parentJob.cancel() parentJob.join() println("End") Thread.sleep(100_000) } ``` ## 捕獲CancellationException以后,要考慮是否應該重新拋出來 ```kotlin fun main() = runBlocking { val parentJob = launch(Dispatchers.IO) { launch() { var i = 0 while (true) { try { delay(500L) } catch (e: CancellationException) { // 這里如果不將CancellationException拋出,那么該協程被取消也不會結束 e.printStackTrace() } i++ println("First i = ${i}") } } launch { var i = 0 while (true) { delay(500L) i++ println("Second i = ${i}") } } } delay(2000L) parentJob.cancel() parentJob.join() println("End") Thread.sleep(100_000) } ``` ## 不要直接使用try-catch直接包裹launch、async 使用`launch`和`async`啟動的協程其實已經是一個封閉的任務,任務內部有自己的異常處理邏輯,再外部進行`try-catch`是無法得到響應的內部異常的,只能捕獲到創建協程時候的異常; ## 靈活使用SupervisorJob,控制異常傳播范圍 `SupervisorJob`目前我只覺得只有當前協程拋出異常才能做到不影響子協程和父協程,如果是子協程拋出異常那么`SupervisorJob`也無能為力。因為創建子協程的時候又會創建一個新的`job`只不過其`parentjob`是`父協程的job`。 ## 使用CoroutineExceptionHandler處理復雜結構的協程異常,它僅在頂層協程中起作用
                  <ruby id="bdb3f"></ruby>

                  <p id="bdb3f"><cite id="bdb3f"></cite></p>

                    <p id="bdb3f"><cite id="bdb3f"><th id="bdb3f"></th></cite></p><p id="bdb3f"></p>
                      <p id="bdb3f"><cite id="bdb3f"></cite></p>

                        <pre id="bdb3f"></pre>
                        <pre id="bdb3f"><del id="bdb3f"><thead id="bdb3f"></thead></del></pre>

                        <ruby id="bdb3f"><mark id="bdb3f"></mark></ruby><ruby id="bdb3f"></ruby>
                        <pre id="bdb3f"><pre id="bdb3f"><mark id="bdb3f"></mark></pre></pre><output id="bdb3f"></output><p id="bdb3f"></p><p id="bdb3f"></p>

                        <pre id="bdb3f"><del id="bdb3f"><progress id="bdb3f"></progress></del></pre>

                              <ruby id="bdb3f"></ruby>

                              哎呀哎呀视频在线观看