Java中Thread 和Runnable 深入理解

Sophie May發表於2019-03-20

Thread 和Runnable 關係

Thread類是介面Runnable的一個實現類。

public class Thread implements Runnable 
複製程式碼

原始碼分析

  • Thread Threa類執行的時候呼叫start()方法,原始碼如下:

Java中Thread 和Runnable 深入理解
呼叫start()方法,實際執行的是start0方法,方法宣告如下:

private native void start0()
複製程式碼

native表明這個方法是個原生函式,即這個函式是用C/C++實現的,被編譯成DLL,由Java呼叫。 native 方法是在註冊是在Thread物件初始化完成的,如圖,靜態塊static裡有個registerNatives方法,該方法會註冊一些本地方法供Thread類使用。

Java中Thread 和Runnable 深入理解

start0方法會在JVM 新建一個執行緒

  • Runnable Runnable 介面只有一個run()方法,完全是執行緒執行規範。

Java中Thread 和Runnable 深入理解

程式碼例項分析

  • Thread類定義一個賣票的類
public class TicketThread extends Thread {

    private int ticket = 100000;

    @Override
    public void run() {
        for (int i = 0; i < 100000; i++) {
            if (ticket > 0) {
                System.out.println("ticket=" + ticket-- + "," + Thread.currentThread().getName());
            }
        }
    }
}
複製程式碼

啟動三個執行緒

new TicketThread().start();
new TicketThread().start();
new TicketThread().start();
複製程式碼

執行發展每個執行緒獨立執行了賣票的任務,每個執行緒中票數依次減1。

  • Runnable介面實現一個賣票的類
public class TicketRunnableThread implements Runnable {
    private int ticket = 1000;
    public void run() {
        for (int i = 0; i < 1000; i++) {
            if (ticket > 0) {
                System.out.println("ticket=" + ticket-- + "," + Thread.currentThread().getName());
            }
        }
    }
}
複製程式碼

啟動三個執行緒

TicketRunnableThread ticketRunnableThread = new TicketRunnableThread();
new Thread(ticketRunnableThread).start();
new Thread(ticketRunnableThread).start();
new Thread(ticketRunnableThread).start();
複製程式碼

三個執行緒共同完成了賣票任務,然而三個執行緒共同執行同一段程式碼,會造成執行緒不安全,可以通過加鎖解決。

使用選擇

  • 實現Runnable介面的同時,還可以繼承其他類,避免Java的單繼承性帶來侷限性。
  • Runnable介面可以實現資源共享,Thread無法完成資源共享。

相關文章