在電腦編程中,一個基本的概念就是同時對多個任務加以控制。許多程式設計問題都要求程式能夠停下手頭的工作,改為處理其他一些問題,再返回主進程。可以通過多種途徑達到這個目的。最開始的時候,那些擁有機器低級知識的程式員編寫一些“插斷服務常式”,主進程的暫停是通過硬體級的中斷實現的。儘管這是一種有用的方法,但編出的程式很難移植,由此造成了另一類的代價高昂問題。
有些時候,中斷對那些即時性很強的任務來說是很有必要的。但還存在其他許多問題,它們只要求將問題劃分進入獨立啟動並執行程式片斷中,使整個程式能更迅速地響應使用者的請求。在一個程式中,這些獨立啟動並執行片斷叫作“線程”(Thread),利用它編程的概念就叫作“多執行緒”。多執行緒一個常見的例子就是使用者介面。利用線程,使用者可按下一個按鈕,然後程式會立即作出響應,而不是讓使用者等待程式完成了當前任務以後才開始響應。
最開始,線程只是用於分配單個處理器的處理時間的一種工具。但假如作業系統本身支援多個處理器,那麼每個線程都可分配給一個不同的處理器,真正進入“並行運算”狀態。從程式設計語言的角度看,多線程操作最有價值的特性之一就是程式員不必關心到底使用了多少個處理器。程式在邏輯意義上被分割為數個線程;假如機器本身安裝了多個處理器,那麼程式會運行得更快,毋需作出任何特殊的調校。
根據前面的論述,大家可能感覺線程處理非常簡單。但必須注意一個問題:共用資源!如果有多個線程同時運行,而且它們試圖訪問相同的資源,就會遇到一個問題。舉個例子來說,兩個進程不能將資訊同時發送給一台印表機。為解決這個問題,對那些可共用的資源來說(比如印表機),它們在使用期間必須進入鎖定狀態。所以一個線程可將資源鎖定,在完成了它的任務後,再解開(釋放)這個鎖,使其他線程可以接著使用同樣的資源。
Java的多線程機制已內建到語言中,這使一個可能較複雜的問題變得簡單起來。對多執行緒的支援是在對象這一級支援的,所以一個執行線程可表達為一個對象。Java也提供了有限的資源鎖定方案。它能鎖定任何對象佔用的記憶體(記憶體實際是多種共用資源的一種),所以同一時間只能有一個線程使用特定的記憶體空間。為達到這個目的,需要使用synchronized關鍵字。其他類型的資源必須由程式員明確鎖定,這通常要求程式員建立一個對象,用它代表一把鎖,所有線程在訪問那個資源時都必須檢查這把鎖。