linuxI O的一些理解

2021-06-18 02:53:27 字數 1360 閱讀 8741

同步i/o(阻塞i/o),非同步i/o(非阻塞)

同步,非同步的概念本來是通訊領域的, 很難解釋清楚, 但我肯定他跟阻塞非阻塞完全沒有任何關係。

在這裡的同步非同步, 我個人的理解是函式呼叫的時候的同步非同步。

其實同步方式很好理解, 例如你呼叫乙個function,   當這個function執行完後,這個方法實現的功能已經完成。這裡往往會跟阻塞混淆,其實是因為你採用了同步方式執行**,才阻塞了你的thread或者process. 而不是因為阻塞,才叫同步。

非同步方式就不提供這種保證, 當你用非同步方式呼叫乙個function的時候,這個方法會馬上返回,事實上多數情況下 這種functioncall只是向某個任務執行體提交乙個任務而已。 而你的主thread可以繼續執行其他的事情, 不必等待(阻塞), 而當那個任務執行體執行完你提交的這個任務後,它會通過某種方法callback給你的thread, 告訴你,你的這個任務已經完成。

實際上,在目前的應用中, 很少有真正實現非同步io的(aio), 聽說(windows完成埠跟bsd kqueue實現了, 只是聽說而已), 而通過select/poll等實現的不能算是aio,只能說是個類似的或者是假冒的。。

因為用select/poll實現的情況下,他們多半都是把呼叫thread作為執行體thread的

1.read/write:

對於read操作來說,它是同步的。也就是說只有當申請讀的內容真正存放到buffer中後(user mode的buffer),read函式才返回。在此期間,它會因為等待io完成而被阻塞。研究過原始碼的朋友應該知道,這個阻塞發生在兩個地方:一是 read操作剛剛發起,kernel會檢查其它程序的need_sched標誌,如果有其它程序需要排程,主動阻塞read操作,這個時候其實i/o操作 還沒有發起。二是i/o操作發起後,呼叫lock_page對已經加鎖的頁面申請鎖,這時由於頁面已經加鎖,所以加鎖操作被阻塞,從而read操作阻塞,直到i/o操作完成後頁面被解鎖,read操作繼續執行。所以說read是同步的,其阻塞的原因如上。

對於write操作通常是非同步的。因為 linux中有page cache機制,所有的寫操作實際上是把檔案對應的page cache中的相應頁設定為dirty,然後write操作返回。這個時候對檔案的修改並沒有真正寫到磁碟上去。所以說write是非同步的,這種方式下 write不會被阻塞。如果設定了o_sync標誌的檔案,write操作再返回前會把修改的頁flush到磁碟上去,發起真正的i/o請求,這種模式下 會阻塞。

2.direct i/o

linux

支援direct i/o, 以o_dircet標誌開啟的檔案,在read和write的時候會繞開pagecache,直接使用user mode的buffer做為i/o操作的buffer。這種情況下的read和write直接發起i/o操作,都是同步的,並會被阻塞。

堆疊的一些理解

堆疊是一種執行 後進先出 演算法的資料結構。設想有乙個直徑不大 一端開口一端封閉的竹筒。有若干個寫有編號的小球,小球的直徑比竹筒的直徑略小。現在把不同編號的小球放到竹筒裡面,可以發現一種規律 先放進去的小球只能後拿出來,反之,後放進去的小球能夠先拿出來。所以 先進後出 就是這種結構的特點。堆疊就是這...

const 的一些理解

以前覺得自己對const還是有些理解的,今天一兄弟問了乙個問題才讓我對這個東西又加深了些了解 class temp public void output void func const temp a a.output 就這麼簡單乙個東西,眨眼一看,沒什麼問題,但是編譯是不會通過的,因為func呼叫了...

VC的一些理解

vc維就是乙個係數,這個係數就是為了度量一組函式集的容量 capacity 注意這裡的 函式 是廣義的,線性函式 多項式函式當然都是函式 對於乙個多層的神經網路,權值大小不知道 訓練神經元網路就是為了確定權值 每組權值就可以認為對應乙個函式。而容量就反映了一組函式集對樣本的區分能力,容量越大,對應的...