現在的位置: 首頁 > 綜合 > 正文

面試——操作系統的基礎知識

2019年03月04日 ⁄ 綜合 ⁄ 共 2990字 ⁄ 字號 評論關閉

1、線程與進程的區別聯繫
2、進程通信方式有哪些?
3、同步的方式有哪些?
4、ThreadLocal與其它同步機制的比較
5、進程死鎖的條件

第一題:
(1)線程是進程的一個實體,一個進程可以擁有多個線程,多個線程也可以並發執行。一個沒有線程的進程也可以看做是單線程的,同樣線程也經常被看做是一種輕量級的進程。並且進程可以不依賴於線程而單獨存在,而線程則不然。
(2)進程是並發程序在一個數據集合上的一次執行過程,進程是系統進行資源分配和調度的獨立單位,線程是進程的實體,它是比進程更小的能夠獨立執行的基本單元,線程自己不擁有任何系統資源,但是它可以訪問其隸屬進程的全部資源。
(3) 與進程的控制塊PCB相似,線程也有自己的控制表TCB,但是TCB中所保存的線程狀態比PCB塊少得多。

進程的作用與定義:是為了提高CPU的執行效率,為了避免因等待而造成CPU空轉以及其他計算機硬件資源的浪費而提出來的。

線程的引入:例如,有一個Web服務器要進程的方式並發地處理來自不同用戶的網頁訪問請求的話,可以創建父進程和多個子進程的方式來進行處理,但是創建一個進程要花費較大的系統開銷和佔用較多的資源。除外,這些不同的用戶子進程在執行的時候涉及到進程上下文切換,上下文切換是一個複雜的過程。所以,為了減少進程切換和創建的開銷,提高執行效率和節省資源,人們在操作系統中引入了"線程(thread)"的概念。

第二題:
進程間通訊的方式:
管道中還有命名管道和非命名管道之分,非命名管道只能用於父子進程通訊,命名管道可用於非父子進程,命名管道就是FIFO,管道是先進先出的通訊方式。FIFO是一種先進先出的隊列。它類似於一個管道,只允許數據的單向流動。每個FIFO都有一個名字,允許不相關的進程訪問同一個FIFO,因此也成為命名管道。
消息隊列:是用於兩個進程之間的通訊,首先在一個進程中創建一個消息隊列,然後再往消息隊列中寫數據,而另一個進程則從那個消息隊列中取數據。需要注意的是,消息隊列是用創建文件的方式建立的,如果一個進程向某個消息隊列中寫入了數據之後,另一個進程並沒有取出數據,即使向消息隊列中寫數據的進程已經結束,保存在消息隊列中的數據並沒有消失,也就是說下次再從這個消息隊列讀數據的時候,就是上次的數據!!!
信號量:不能傳遞複雜消息,只能用來同步
共享內存:只要首先創建一個共享內存區,其它進程按照一定的步驟就能訪問到這個共享內存區中的數據,當然可讀可寫;

幾種方式的比較

管道:速度慢,容量有限
消息隊列:容量受到系統限制,且要注意第一次讀的時候,要考慮上一次沒有讀完數據的問題。
信號量:不能傳遞複雜消息,只能用來同步
共享內存區:能夠很容易控制容量,速度快,但要保持同步,比如一個進程在寫的時候,另一個進程要注意讀寫的問題,相當於線程中的線程安全,當然,共享內存區同樣可以用作線程間通訊,不過沒這個必要,線程間本來就已經共享了一塊內存的。

第三題:
線程同步指多個線程同時訪問某資源時,採用一系列的機制以保證同時最多只能一個線程訪問該資源。線程同步是多線程中必須考慮和解決的問題,因為很可能發生多個線程同時訪問(主要是寫操作)同一資源,如果不進行線程同步,很可能會引起數據混亂,造成線程死鎖等問題;

線程同步的方式:

臨界區:通過對多線程的串行化來訪問公共資源或者一段代碼,速度快,適合控制數據訪問
互斥量:採用互斥對象機制,只有擁有互斥對象的線程才有訪問公共資源的權限,因為互斥對象只有一個,所以可以保證公共資源不會同時被多個線程訪問
信號量:它允許多個線程同一時刻訪問同一資源,但是需要限制同一時刻訪問此資源的最大線程數目。信號量對象對線程的同步方式與前面幾種方法不同,信號允許多個線程同時使用共享資源,這與操作系統中PV操作相似。
事件(信號):通過通知操作的方式來保持多線程的同步,還可以方便的實現多線程的優先級比較的操作


總結比較: 

互斥量與臨界區的作用非常相似,但互斥量是可以命名的,也就是說它可以跨越進程使用。所以創建互斥量需要的資源更多,所以如果只為了在進程內部是用的話使用臨界區會帶來速度上的優勢並能夠減少資源佔用量。因為互斥量是跨進程的互斥量一旦被創建,就可以通過名字打開它。
互斥量(Mutex),信號燈(Semaphore),事件(Event)都可以被跨越進程使用來進行同步數據操作,而其他的對象與數據同步操作無關,但對於進程和線程來講,如果進程和線程在運行狀態則為無信號狀態,在退出後為有信號狀態。所以可以使用WaitForSingleObject來等待進程和線程退出。
通過互斥量可以指定資源被獨佔的方式使用,但如果有下面一種情況通過互斥量就無法處理,比如現在一位用戶購買了一份三個並發訪問許可的數據庫系統,可以根據用戶購買的訪問許可數量來決定有多少個線程/進程能同時進行數據庫操作,這時候如果利用互斥量就沒有辦法完成這個要求,信號燈對象可以說是一種資源計數器。

第四題:

Threadlocal和其他所有的同步機制都是為了解決多線程中的對同一變量的訪問衝突,在普通的同步機制中,是通過對對象加鎖來實現多個線程對同一變量的安全訪問的。這時該變量是多個線程共享的,使用這種同步機制需要很細緻的分析在什麼時候對變量進行讀寫,什麼時候需要鎖定某個對象,什麼時候釋放該對象的索等等。所有這些都是因為多個線程共享了該資源造成的。Threadlocal就從另一個角度來解決多線程的並發訪問,Threadlocal會為每一個線程維護一個和該線程綁定的變量副本,從而隔離了多個線程的數據共享,每一個線程都擁有自己的變量副本,從而也就沒有必要對該變量進行同步了。ThreadLocal提供了線程安全的共享對象,在編寫多線程代碼時,可以把不安全的變量封裝進ThreadLocal。
總結:當然ThreadLocal並不能替代同步機制,兩者面向的問題領域不同。同步機制是為了同步多個線程對相同資源的並發訪問,是為了多個線程之間進行通信的有效方式;而ThreadLocal是隔離多個線程的數據共享,從根本上就不在多個線程之間共享資源(變量),這樣當然不需要對多個線程進行同步了。所以,如果你需要進行多個線程之間進行通信,則使用同步機制;如果需要隔離多個線程之間的共享衝突,可以使用ThreadLocal,這將極大地簡化你的程序,使程序更加易讀、簡潔。

第五題:

首先回答死鎖的定義,所謂死鎖就是一個進程集合中的多個進程因為競爭資源,而造成的互相等待現象。
死鎖的原因:系統資源不足;多個進程的推進順序不合理
死鎖的必要條件:
互斥條件(Mutual exclusion):資源不能被共享,只能由一個進程使用。
請求與保持條件(Hold and wait):已經得到資源的進程可以再次申請新的資源。
非剝奪條件(No pre-emption):已經分配的資源不能從相應的進程中被強制地剝奪。
循環等待條件(Circular wait):系統中若干進程組成環路,改環路中每個進程都在等待相鄰進程正佔用的資源。

處理死鎖的策略:

忽略該問題。例如鴕鳥算法,該算法可以應用在極少發生死鎖的情況下。傳說中,鴕鳥看到危險就把頭深埋地下,這是顯然是一種很消極的策略。
檢測死鎖並且恢復。
通過對資源有序分配,以避免循環等待的“環路”發生。
通過破壞死鎖的必要條件,來防止死鎖的產生。

抱歉!評論已關閉.