<kbd id="afajh"><form id="afajh"></form></kbd>
<strong id="afajh"><dl id="afajh"></dl></strong>
    <del id="afajh"><form id="afajh"></form></del>
        1. <th id="afajh"><progress id="afajh"></progress></th>
          <b id="afajh"><abbr id="afajh"></abbr></b>
          <th id="afajh"><progress id="afajh"></progress></th>

          「Go實戰(zhàn)系列」調(diào)度的本質(zhì)

          共 1567字,需瀏覽 4分鐘

           ·

          2021-09-02 20:02

          這個系列會講一些從課程中學到的讓人醍醐灌頂?shù)臇|西,撥云見日,帶你重新認識 Go。

          上周課程已經(jīng)開始了,曹大直播了第一期,干貨滿滿,大呼過癮。第一課之后,陸續(xù)又加進來了一些同學。

          首先拋出本文的結論:Go 調(diào)度的本質(zhì)是一個生產(chǎn)-消費流程。

          生產(chǎn)者-消費者

          生產(chǎn)者-消費者模型

          我們平時用 Go 最爽的一點莫過于用一句 go func(){}() 就啟動了一個 goroutine 來并發(fā)地執(zhí)行任務。這比用 C/C++ 啟動一個線程并發(fā)地去執(zhí)行任務方便太多。這句代碼實際上就生產(chǎn)出了一個 goroutine,并進入可運行隊列,等待和 m 來找它從而可以得到運行。

          熟悉 GMP 模型的朋友都知道,goroutine 最終在 m 上得以執(zhí)行,因為操作系統(tǒng)感知不到 goroutine,它只能感知線程,并且線程可以看成是 m。

          所以,m 拿到 goroutine 并運行它的過程就是一個消費過程。

          生產(chǎn)-消費過程

          生產(chǎn)過程——三級隊列

          生產(chǎn)出的 goroutine 需要找一個地方存放,這個地方就是可運行隊列。在 Go 程序中,可運行隊列是分級的,分為三級:

          三級可運行隊列

          runnext 實際上只能指向一個 goroutine,所以它是一個特殊的隊列。

          那把 goroutine 放到哪個可運行隊列呢?看情況。

          首先,如果 runnext 為空,那么 goroutine 就會順利地放入 runnext,接下來,它會以最高優(yōu)先級得到運行,即優(yōu)先被消費。

          如果 runnext 不為空,那就先負責把 runnext 上的 old goroutine 踢走,再把 new goroutine 放上來。具體踢到哪里呢?又得分情況。

          local queue 是一個大小為 256 的數(shù)組,實際上用 head 和 tail 指針把它當成一個環(huán)形數(shù)組在使用。如果 local queue 不滿,則將 runnext 放入 local queue;否則,P 的本地隊列上的 goroutine 太多了,說明當前 P 的任務太重了,需要減負,因此需要得到其他 P 協(xié)助。從而,將 runnext 以及當前 P 的一半 goroutine 一起打包丟到 global queue 里去。

          當然,這部分課程里有非常生動的動畫,這里貼一個截圖大家感受一下:

          生產(chǎn)者動畫

          消費過程——調(diào)度循環(huán)

          之前的文章里也講到過調(diào)度循環(huán)是咋回事,它實際上就是 Go 程序在啟動的時候,會創(chuàng)建和 CPU 核心數(shù)相等個數(shù)的 P,會創(chuàng)建初始的 m,稱為 m0。這個 m0 會啟動一個調(diào)度循環(huán):不斷地找 g,執(zhí)行,再找 g……

          偽代碼是這樣的:

          調(diào)度循環(huán)

          隨著程序的運行,m 更多地被創(chuàng)建出來,因此會有更多的調(diào)度循環(huán)在執(zhí)行。

          那邊生產(chǎn)者在不斷地生產(chǎn) g,這邊 m 的調(diào)度循環(huán)不斷地在消費 g,整個過程就 run 起來了。

          找 g 的過程中當然也是從上面的三級隊列里找:

          先看 runnext,再看 local queue,再看 global queue。當然,如果實在找不到,就去其他 p 去偷。

          總結

          今天的文章只用記住一個觀點:Go 調(diào)度的本質(zhì)是一個生產(chǎn)-消費流程。這個觀點非常新穎,之前我沒有從哪篇文章看到過,這是曹大自己的感悟。

          讀者即使之前沒見過類似的說法,但是一旦聽曹大講出來,就馬上感覺醍醐灌頂。

          這種熟悉加意外的效果其實就是你成長的時機。

          想要獲取了解更多 「Go 實戰(zhàn)」的相關信息,趕緊掃碼進群哦~


          如果群滿,可加小助手,就能拉你一起加入群聊啦





          瀏覽 67
          點贊
          評論
          收藏
          分享

          手機掃一掃分享

          分享
          舉報
          評論
          圖片
          表情
          推薦
          點贊
          評論
          收藏
          分享

          手機掃一掃分享

          分享
          舉報
          <kbd id="afajh"><form id="afajh"></form></kbd>
          <strong id="afajh"><dl id="afajh"></dl></strong>
            <del id="afajh"><form id="afajh"></form></del>
                1. <th id="afajh"><progress id="afajh"></progress></th>
                  <b id="afajh"><abbr id="afajh"></abbr></b>
                  <th id="afajh"><progress id="afajh"></progress></th>
                  精品无人区一区二区三区聊斋艳谭 | 思思热高清无码播放 | 在线观看黄片视频 | 激情五月天成人网 | 久久久久久久久黄色 |