異步 同步 阻塞 非阻塞

http://blog.csdn.net/historyasamirror/article/details/5778378編程

首先說明我對這些概念也不是很清楚,如下內容是我作的一些理事。網絡

同步和異步、阻塞和非阻塞這是兩組概念,說的是不一樣的事情,同步和阻塞沒有必然的聯繫,異步和非阻塞也沒有必然的聯繫。同步和異步是隻跟IO操做過程當中進程的狀態變化有關。阻塞和非阻塞就是進程的兩種狀態。好比你去銀行,排除的話就是一種同步的方式,叫號的話就是異步的方式。排隊必須本身看着何時輪到本身,而叫號則沒必要,輪到你的時候會觸發一個事件,或者說你會收到一個信號,別人會叫你。無論是排除仍是叫號,若是你在等待的過程當中不能作其餘事情,那就是阻塞模式,不然就是非阻塞模式。同步的時候能夠有阻塞和非阻塞,異步的時候也能夠有阻塞和非阻塞。異步

阻塞 I/O

Linux下的I/O操做默認是阻塞I/O,即open和socket建立的I/O都是阻塞I/O。當讀寫操做沒有完成時,函數就不會返回,進程一直阻塞在那裏。socket

非阻塞I/O    

非阻塞模式的使用並不廣泛,由於非阻塞模式會浪費大量的CPU資源。
函數

網絡編程時listen,recvfrom,connect都會引發阻塞。非阻塞IO一般應用於網絡編程中,IO請求時加上O_NONBLOCK一類的標誌位,函數馬上返回,IO沒有就緒會返回錯誤,須要請求進程主動輪詢不斷髮IO請求直到返回正確
好比調用recvfrom時,若是系統尚未接收到網絡數據,內核立刻返回一個 EWOULDBLOCK的錯誤。
測試

 當一個應用程序使用了非阻塞模式的套接字,它須要使用一個循環來不停地測試是否一個文件描述符有數據可讀(稱作 polling(輪詢))。應用程序不停的 polling 內核來檢查是否 I/O操做已經就緒。這將是一個極浪費 CPU資源的操做。這種模式使用中不是很廣泛。spa

I/O多路複用

針對批量IP操做時,使用I/O多路複用,很是有好。.net

在使用 I/O 多路技術的時候,咱們調用 select()函數和 poll()函數或epoll函數(2.6內核開始支持),在調用它們的時候阻塞。
當咱們調用 select函數阻塞的時候,select 函數等待數據報套接字進入讀就緒狀態。當select函數返回的時候, 也就是套接字能夠讀取數據的時候。 這時候咱們就能夠調用 recvfrom函數來將數據拷貝到咱們的程序緩衝區中。
IO複用同非阻塞IO本質同樣,不過利用了新的select系統調用,由內核來負責原本是請求進程該作的輪詢操做。看似比非阻塞IO還多了一個系統調用開銷,不過由於能夠支持多路IO,纔算提升了效率。多路複用的高級之處在於:它能同時等待多個文件描述符,而這些文件描述符(套接字描述符)其中的任意一個進入讀就緒狀態,select()函數就能夠返回。

異步I/O

      當咱們運行在異步 I/O 模式下時,咱們若是想進行 I/O 操做,只須要告訴內核咱們要進行 I/O 操做,而後內核會立刻返回。具體的 I/O 和數據的拷貝所有由內核來完成,咱們的程序能夠繼續向下執行。當內核完成全部的 I/O 操做和數據拷貝後,內核將通知咱們的程序。
相關文章
相關標籤/搜索