2016-12-30 41 views
1

目標是創建搜索方法,該方法返回首先在所有搜索線程中找到的針的索引。當其中一個完成時,我需要停止所有線程。當其中一個完成時停止所有線程

邏輯是:有4個線程。第一個線程首先檢查乾草堆的%25,第二個線程檢查乾草堆的%25-%50等等。

只要其中一人打印文字,我就應該停下來,但我總是得到4個輸出,因爲他們中的4人都發現了大海撈針。但是,我只需要一個輸出。

實施例輸出:(下面索引)

I found, it is: 622 
I found, it is: 4072 
I found, it is: 7519 
I found, it is: 7264 

這裏是SearcherThreat類的擴展Thread

public class SearcherThread extends Thread { 

// PROPERTIES 
private int needle; 
private int[] haystack; 
private int start, end; 

// CONSTRUCTOR 
public SearcherThread(int needle, int[] haystack, int start, int end) { 
    this.needle = needle; 
    this.haystack = haystack; 
    this.start = start; 
    this.end = end; 
} 

@Override 
public void run() { 
    for (int i = start; i < end && !isInterrupted(); ++i) { 
     if (haystack[i] == needle) { 
      System.out.println("I found, it is: " + i); 
      for (SearcherThread searcher : InterruptTest.searchers) { 
       searcher.interrupt(); 
      } 

     } 
    } 
} 
} 

這是包含主類和線程

import java.util.ArrayList; 
public class InterruptTest { 

public static ArrayList<SearcherThread> searchers = new ArrayList<SearcherThread>(); 

public static void main(String[] args) throws InterruptedException { 

    int itemCount = 10000; 
    int[] haystack = new int[itemCount]; 
    int domainSize = 1000; 
    for (int i = 0; i < itemCount; ++i) 
     haystack[i] = (int) (Math.random() * domainSize); 
    int needle = 10; 

    int numThreads = 4; 
    int numItemsPerThread = haystack.length/numThreads; 
    int extraItems = haystack.length - numItemsPerThread * numThreads; 
    for (int i = 0, start = 0; i < numThreads; ++i) { 
     int numItems = (i < extraItems) ? (numItemsPerThread + 1) : numItemsPerThread; 
     searchers.add(new SearcherThread(needle, haystack, start, start + numItems)); 
     start += numItems; 
    } 

    for (SearcherThread searcher : searchers) 
     searcher.start(); 
} 
} 
+0

我這樣做,但爲什麼我得到4輸出 –

+0

因爲您的工作線程不檢查,看他們是否中斷。 –

+0

我可能在這裏找到了答案http://stackoverflow.com/questions/41389714/threading-search-for-a-value-and-stop-all-threads –

回答

4

我得到了這個輸出:

[[email protected] tmp]$ java InterruptTest 
I found, it is: 855 
I found, it is: 3051 
[[email protected] tmp]$ java InterruptTest 
I found, it is: 2875 
I found, it is: 5008 
I found, it is: 1081 
I found, it is: 8527 
[[email protected] tmp]$ java InterruptTest 
I found, it is: 2653 
I found, it is: 5377 
I found, it is: 1092 
[[email protected] tmp]$ java InterruptTest 
I found, it is: 255 
I found, it is: 9095 
I found, it is: 6983 
I found, it is: 3777 

正如您所看到的,完成的線程數從一次運行到下一次不等。

我們這裏有一場比賽。可能發生的情況是,一個線程在啓動之前完成並中斷其他線程。所以他們看不到中斷。 javadoc說:

「中斷不活動的線程不需要任何效果。」

另一種可能性是中斷傳播速度不夠快。請注意,javadoc沒有說中斷的線程立即可見interrupt()

我想不出一個解決方案,這並不否定多線程的好處。另一方面,在現實世界的用例中:

  • 您應該使用線程池......因爲線程創建相對較貴。
  • 線程應該做更多的工作。

如果您測量了您在當前測試中獲得的實際加速比,那麼可能是否定


綜上所述,在更真實的測試,你應該看到中斷工作大部分時間。這應該足夠好。 (應該沒有關係,偶爾線程不會中斷得足以阻止他們發現二級結果。)

+0

+1此外,如果在發送中斷後打印消息並在線程中斷時打印消息,則會看到多次線程由於種族條件,其他時間會中斷,要麼他們發現針速過快,要麼中斷不是立即發生。可能是 – Gray

+0

。但是,添加跟蹤打印時需要小心一點。他們可以改變多線程代碼的行爲 –

相關問題