Junit單元多線程測試子線程不執行,junit多線程
Junit單元測試子線程不執行
Junit單元測試子線程不執行
環境
- Junit:4
- jdk:1.8
1、現象描述
在測試CountDownLatch類時,使用main函數能夠正常啟動並執行功能,改用Junit測試時,Debug調試時不進入子線程執行,直接運行時,有時候能夠執行子線程中的部分代碼,具體程式如下:
import org.junit.Test;import java.util.concurrent.CountDownLatch;/*** @ClassName: CountDownLatchTest* @Description: CountDownLatch測試類別* @author Yue Chang * @date 2018年1月16日 上午11:31:26 * @since 1.0*/public class CountDownLatchTest { @Test public void test() throws InterruptedException { CountDownLatch latch = new CountDownLatch(1); MyThread myThread = new MyThread(latch); Thread t1 = new Thread(myThread); t1.setName("t1"); Thread t2 = new Thread(myThread); t2.setName("t2"); t1.start(); t2.start(); } public static void main(String[] args) { CountDownLatch latch = new CountDownLatch(1); MyThread myThread = new MyThread(latch); Thread t1 = new Thread(myThread); t1.setName("t1"); Thread t2 = new Thread(myThread); t2.setName("t2"); t1.start(); t2.start(); }}class MyThread implements Runnable{ private CountDownLatch latch; private volatile int number; /** * @param latch */ public MyThread(CountDownLatch latch) { this.latch = latch; } public MyThread() { } public CountDownLatch getLatch() { return latch; } public void setLatch(CountDownLatch latch) { this.latch = latch; } public int getNumber() { return number; } public void setNumber(int number) { this.number = number; } public void run() { String threadName = Thread.currentThread().getName().trim(); if ("t2".equals(threadName)) { // t2線程 try { Thread.sleep(5000); System.out.println("線程0:" + threadName); } catch (InterruptedException e) { e.printStackTrace(); } this.setNumber(1); latch.countDown(); // 計數減1 } else if ("t1".equals(threadName)) { // t1線程 try { System.out.println("線程1:" + threadName); latch.await(); // 阻塞等待計數為0 System.out.println("線程1:" + threadName); } catch (InterruptedException e) { e.printStackTrace(); } System.out.println("num = " + this.getNumber()); } }}
2、執行結果
執行Junit結果如下:
線程1:t1
或者是什麼都沒有列印
執行main結果如下:
線程1:t1線程0:t2線程1:t1num = 1
執行t1時,由於countDownLatch值還不為0,於是將處於等待中,知道t2執行完,將countDownLatch的值減1,變為0時,t1才繼續執行,最後列印出num。
3、分析
後面尋找資料才知道Junit當主線程退出,子線程也會退出。這樣一來也就可以解釋為什麼有時候執行部分,有時候完全沒有執行這個現象了。
4、解決辦法:
在Junit測試代碼中,加上如下代碼:
// junit主線程執行完之後,不會再去管子線程的執行情況,如果沒有join(),那麼大多數情況下子線程沒法執行完t1.join();
讓主線程等待t1線程執行完,也就可以讓子線程正常執行了
查看評論