JAVA知識之多線程(一):基礎知識

JAVA知識之多線程(一)

1.線程是什麼?進程又是什麼?

線程是程序運行的基本單位,所有的命令都在線程中運行。進程可以是獨立運行的一段功能。

進程是由一個或者多個線程組成的,且一個進程至少包含有一個線程,可以認爲線程是進程的子集。程序執行時,系統資源會分配給進程,同一個進程內的線程都使用這個進程裏的系統資源。

定義很難理解是吧?我舉個例子就簡單多了:我們平時工作和生活中經常使用電腦,常常會同時運行多個程序,比如我們一邊用QQ聊天,一邊打開淘寶網挑選商品,那麼瀏覽器和QQ程序就各自對應了一個進程,當我們給朋友發送了一個微笑的表情時,QQ進程裏的發送消息線程就開始執行了,當我們在網上選中一個商品加入了購物車,那麼瀏覽器就會執行發送添加商品到購物車的命令給網站。QQ和瀏覽器是兩個獨立的進程,即使其中一個進程關閉了,另一個進程也不會有影響,如果我關閉了QQ進程,那麼發送消息和接收消息的線程就都不能工作了,但是瀏覽器依然可以上網購物,這就是線程和進程的區別了。

2.線程如何創建?

創建線程有三種辦法:繼承Thread類、實現Runnable接口、實現Callable接口。

  • 繼承Thread類

    1.新建一個類,繼承Thread類(注意Thread本身也是實現了Runnable接口)
    2.重寫run()方法
    3.創建線程類的對象來創建線程
    4.調用線程對象的start()方法,線程開啓

public class ThreadTest extends Thread {

    //重寫run方法,run方法內就是線程執行的代碼
    public void run(){
        for(int i=1; i<=5; i++){
            System.out.println("輸出數字:"+ i);
        }
    }

    public static void main(String args[]){
        //創建線程對象
        ThreadTest thread = new ThreadTest();
        //調用start方法開啓線程,此時線程是可運行狀態(Runnable狀態),等待執行,不一定立刻執行。
        thread.start();
    }
}

程序執行run(),輸出數字1~5,結果如下:

  • 實現Runnable接口
    1.新建一個類,實現Runnable接口
    2.重寫run()方法
    3.創建Thread類的對象來創建線程,並把Runnable接口的實現類對象作爲參數傳入,定義線程執行的內容
    4.調用線程的start()方法,線程開啓
public class RunnableTest implements Runnable {

    //重寫run方法,run方法就是線程內執行的代碼
    public void run(){
        for(int i=1; i<=5; i++){
            System.out.println("輸出數字:"+ i);
        }
    }

    public static void main(String args[]){
        //創建線程執行的對象
        RunnableTest r = new RunnableTest();
        //創建線程的對象,傳入線程執行的內容,也就是包含run方法內容的RunnableTest對象
        Thread thread = new Thread(r);
        //調用start方法開啓線程,此時線程是可運行狀態(Runnable狀態),等待執行,不一定立刻執行。
        thread.start();
    }
}

結果如下:

  • 實現Callable接口
    1.新建一個類,實現Callable接口
    2.重寫call()方法
    3.創建callable接口子類對象
    4.創建線程池
    5.提交線程給線程池開啓線程,並返回Future對象
    6.處理Future對象
public class CallableTest implements Callable {

    //重寫call方法,call方法就是線程內執行的代碼,和run方法作用相同,可以有返回值
    public String call() throws Exception{
        return("這是個有返回值的線程");
    }

    public static void main(String args[]){
        //創建線程池
        ExecutorService es = Executors.newFixedThreadPool(3);
        CallableTest c = new CallableTest();
        //提交線程任務開啓線程,返回Future對象
        Future future = es.submit(c);
        try {
            String str = (String) future.get();
            System.out.println(str);
        } catch (Exception e) {
            e.printStackTrace();
        } finally{
        // 線程池關閉
            es.shutdown();
        }
    }
}

結果如下:

3.總結

  • 繼承Thread類和實現Runnable接口都是執行Runnable接口的run()方法,而實現Callable接口是執行Callable接口的call()方法。
  • run方法和call()方法都是封裝了程序執行代碼,真正啓動線程的是start()方法,然後再由jvm去選擇執行哪個線程的代碼
  • run()方法沒有返回值,不能拋出異常,call()方法可以有返回值,可以拋出異常。
  • 執行callable任務返回Future對象
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章