關於協程,網上能看到不少資料。這裏再自個梳理一下。算法
協程展開來講,叫作協做的程序,想表達的意思是,兩段程序,能協做地,共用公共資源,來完成兩段程序各自的目的,就叫作協程了。數據結構
把如今全部的容易混淆的名字羅列出來:併發,並行,進程,線程,協程。說說他們的歷史。併發
首先是併發,併發的概念是很早就有的了。最先的時候機器都是批處理系統,並且是單道批處理系統,這個系統就是很簡單的線性邏輯,一個批處理任務進去,完成,而後進行下面一個。可是隨着批處理的任務愈來愈多,咱們但願的是能一次性預存不少批處理任務進入內存,而後經過必定的處理規則指定(做業調度算法)來讓這些批處理任務劃分CPU的時間,這樣CPU的狀態就像是第一秒執行A任務,第二秒執行B任務,這樣看起來,A任務和B任務就像是同時在進行。這個模式,就叫作併發了。函數
能併發處理多任務的系統就是多道程序系統。可是有個問題是,CPU在多個批處理任務切換的過程當中,對於共享變量,堆棧都須要不斷地變化和切換。那麼這個時候,就引入了進程的概念,進程就是CPU處理的基本單元。每一個進程有本身的上下文,堆棧,共享變量。就像一個盒子,把每一個批處理任務和對應的資源都分割開了。性能
下面,隨着CPU硬件技術的發展,一臺機器上CPU的數量就不止一個了,那麼這個時候,兩個CPU就能夠同時,單獨處理兩個進程了。注意,這個同時纔是真正的同時,那麼這個模式,就叫作並行。線程
線程的概念出現,是因爲進程以前的切換須要消耗的資源太多了,不少時候,咱們程序的性能都消耗在進程資源切換上了,因此咱們但願的是,能不能將進程切換過程當中的資源減小?這裏須要深刻到進程的切換,進程控制塊(PCB)是系統爲了管理進程設置的一個專門的數據結構,進程切換的時候,把舊的進程的狀態存入到PCB,而後再加載裝入新的進程的PCB。PCB裏面的信息包含有:程序計數器,寄存器,變量,進程資源等信息。進程之間的切換須要把這些都進行上下文切換,最麻煩耗時的就是切換頁表了,頁表中存儲的是數據段和代碼段。這裏就須要線程的概念,一個進程中有多個線程,同一個進程中的線程共用代碼資源,數據資源,內存資源。因此當同一個進程中的線程進行切換的時候,咱們只須要切換計數器,寄存器,變量,並不須要進行切換頁表操做,這樣,基本建立一個線程比建立一個進程速度要快10-100倍。協程
無論是進程切換仍是線程切換,咱們都須要從系統調用開始,即切換必須涉及到用戶態和內核態的函數調用。那麼,就有人思考,咱們是否是能夠本身實現一個調度邏輯,讓線程的邏輯切換隻在用戶態進行呢?這樣,線程的切換開銷就更小了,這個就是用戶態線程。進程
下面就說到協程了。無論是怎麼個作法,調度算法對於程序來講都是「被動」式的。不免會遇到這種狀況,咱們的程序還在IO等待中,結果調度算法把CPU的時間還分配回來給我,雖然我能夠經過調度算法當即檢查並交出CPU,可是這裏仍是有一個切換的過程。因此就有人思考,是否是能夠作成「主動式」的呢?由程序來告訴計算機,我執行到這裏了,下面進行等待IO行爲了,這個時候就把CPU的控制權交給別人吧。可是,這個實現的基礎固然是調度算法是用戶態的。因此,協程就是在用戶態線程中,兩個程序協商好了,經過某種方式協做運營,共享CPU控制權的方法。內存
通常來講,這個協商的方法通用的關鍵字就是yield。資源