2012-09-14 24 views
1

我在網上看到了下面的例子:
Java線程的行爲

public class TwoThreads { 
public static class Thread1 extends Thread { 
    public void run() { 
     System.out.println("A"); 
     System.out.println("B"); 
    } 
} 
public static class Thread2 extends Thread { 
    public void run() { 
     System.out.println("1"); 
     System.out.println("2"); 
    } 
} 
public static void main(String[] args) { 
    new Thread1().start(); 
    new Thread2().start(); 
} 

}


我的問題是:

  1. 這是保證 「A」 將是打印在「2」之前將打印「B」和「1」之前,但是有可能「1」會由另一個線程連續打印兩次?在這片c我們至少有3個線程(1個主線程和2個線程)。我們可以想象調度器運行1個線程:new Thread1()。start();然後在System.out.println(「1」)後立即放棄;然後再次在Thread1()中運行另一個威脅。再次打印「1」?

  2. 我正在使用NetBeans IDE,它似乎運行這樣的程序總是會導致相同的第一個結果,所以它似乎有一些與緩存。根據我的理解,你通過聲明volatile變量來處理這個問題,它可以在這裏完成,怎麼做?如果不是,那麼緩存的解決方案是什麼?在當今的計算機處理器中,我們大多有2個處理器,而且我們仍然發現網上的許多多線程程序使用2個以上的線程!這個過程在編譯時變得沉重而緩慢嗎?

+0

我從來不理解這些問題。如果你想要一個特定的訂單,爲什麼你使用線程呢? – EJP

回答

0

回答你的1/2問題: 雖然線程運行並行代碼裏面的run方法總是按順序執行。

回答你的3個問題,你可以最好地調整你的。如果處理器數量=線程數量,應用程序,但這不是一個完整的事實,因爲如果線程正在等待某些阻塞操作,那麼它會導致未優化的性能,因爲在那段時間內可以運行另一個線程。

1

1)不能保證線程按什麼順序進行。

2)訂單也沒有隨機化,但是。因此,如果您在相同(或非常相似)的條件下運行程序,它可能會產生相同的線程交錯。如果你需要有一定的行爲(包括隨機行爲),你需要自己同步事物。 3)具有兩個內核的CPU只能同時運行兩個線程,但大多數線程花費的大部分時間並不是實際使用CPU,而是等待I/O或用戶交互等內容。所以你可以從兩個以上的線程中獲得很多(只有兩個線程可以併發計算,但有數百個可以同時等待)。查看一下node.js,這是一種最近流行的多線程編程替代方案,它可以爲併發請求提供巨大的吞吐量,同時只有一個執行線程。

0
  1. 不是,你沒有以任何方式同步你的線程,所以確切的執行順序將受到調度器的支配。鑑於你的線程是如何實現的,我沒有看到你如何能夠通過單個線程兩次打印「1」(或「A」)。

  2. 什麼緩存?什麼變量?您的示例代碼沒有變量,因此沒有適合與volatile關鍵字一起使用的內容。運行此程序的特定機器很可能總會產生相同的結果。如#1所述,您處於調度程序的擺佈之中。如果調度程序總是以相同的方式運行,您將始終得到相同的結果。緩存與它無關。

  3. 這取決於線程在做什麼。如果每個線程都有足夠的工作來將一個CPU核心加載到100%,那麼是的,擁有比CPU核心更多的線程是毫無意義的。但是,這種情況非常少見。許多線程將花費大部分時間睡眠,或等待I/O完成,或者做其他要求不足以完全加載CPU內核的事情。在這種情況下,CPU核心擁有更多的線程沒有任何問題。事實上,多線程早於主流多核CPU,甚至在我們沒有多個CPU內核的時代,能夠擁有多個線程仍然是非常有益的。

+0

你好。
問題1)因爲我的程序沒有同步,在這段代碼中我們至少有3個線程(1個主線程和2個線程)。我們可以想象調度器運行1個線程:new Thread1()。start();然後在System.out.println(「1」)後立即放棄;那麼再以同樣的方式運行另一個威脅? – user1207965