線程經常使用操做方法

在多線程中全部的操做方法都是從Thread類開始的,全部的操做基本上都在Thread類中。java

 

1,線程名稱

  1,在Thread類中能夠經過getName()方法取得線程名稱,經過setName()設置線程名稱。多線程

  2,線程的名稱通常在啓動線程前設置,但也容許爲運行的線程設置名稱,容許兩個Thread對象有相同名稱,可是應該避免。學習

  3,若是程序沒有爲線程指定名稱,系統會自動爲線程設置名稱。spa

class MyThread implements Runnable{    // 實現Runnable接口
    public void run(){    // 覆寫run()方法
        for(int i=0;i<3;i++){
            System.out.println(Thread.currentThread().getName() + "運行,i = " + i) ;    // 取得當前線程的名字
        }
    }
};
public class ThreadNameDemo{
    public static void main(String args[]){
        MyThread mt = new MyThread() ;    // 實例化Runnable子類對象
       new Thread(mt).start() ; // 系統自動設置線程名稱
        new Thread(mt,"線程-A").start() ;        // 手工設置線程名稱
        new Thread(mt,"線程-B").start() ; // 手工設置線程名稱
        new Thread(mt).start() ;        // 系統自動設置線程名稱
        new Thread(mt).start() ;        // 系統自動設置線程名稱
    }
};

 

currentThread(),獲取當前線程。

 運行結果:操作系統

線程-A運行,i = 0
線程-B運行,i = 0
Thread-1運行,i = 0
Thread-0運行,i = 0
Thread-0運行,i = 1
Thread-0運行,i = 2
Thread-1運行,i = 1
線程-B運行,i = 1
Thread-2運行,i = 0
線程-A運行,i = 1
Thread-2運行,i = 1
線程-B運行,i = 2
Thread-1運行,i = 2
Thread-2運行,i = 2
線程-A運行,i = 2

  從效果看,指定的名稱會自動出現,若是沒有指定會發現線程使用自動編號完成,按照Thread-0,Thread-1.依次編號,實際上,確定在類中存在static屬性,用於記錄編號線程

2,當前線程:CurrentThread()

  程序能夠經過currentThread()方法取得當前正在運行的線程對象,code

class MyThread implements Runnable{    // 實現Runnable接口
    public void run(){    // 覆寫run()方法
        for(int i=0;i<3;i++){
            System.out.println(Thread.currentThread().getName()
                    + "運行,i = " + i) ;    // 取得當前線程的名字
        }
    }
};
public class CurrentThreadDemo{
    public static void main(String args[]){
        MyThread mt = new MyThread() ;    // 實例化Runnable子類對象
        new Thread(mt,"線程").start() ;        // 啓動線程
       mt.run() ;    // 直接調用run()方法
    }
};

  運行結果:對象

main運行,i = 0
線程運行,i = 0 main運行,i = 1
線程運行,i = 1 main運行,i = 2
線程運行,i = 2

  此時發現,程序中由主方法直接經過線程對象調用裏面的run()方法,全部此時的結果包含一個"main",此線程就是由「mt.run()」產生的,由於調用此語句是由主方法完成的。blog

也就是說,主方法自己也是一個線程---主線程接口

  問題:既然主方法都是以線程的形式出現,那麼JAVA啓動時候運行了多少線程?

  回答:至少啓動了兩個。

    從以前學習的狀況來看,每當JAVA執行,都會啓動一個JVM,每個JVM都是在操做系統中啓動一個線程。

    JAVA自己有垃圾回收機制,因此至少啓動了兩個線程:主線程,GC。

3,判斷線程是否在執行:isAlive

  

class MyThread implements Runnable{    // 實現Runnable接口
    public void run(){    // 覆寫run()方法
        for(int i=0;i<3;i++){
            System.out.println(Thread.currentThread().getName()
                    + "運行,i = " + i) ;    // 取得當前線程的名字
        }
    }
};
public class ThreadAliveDemo{
    public static void main(String args[]){
        MyThread mt = new MyThread() ;    // 實例化Runnable子類對象
        Thread t = new Thread(mt,"線程");        // 實例化Thread對象
        System.out.println("線程開始執行以前 --> " + t.isAlive()) ;     // 判斷是否啓動
        t.start() ;    // 啓動線程
        System.out.println("線程開始執行以後 --> " + t.isAlive()) ;     // 判斷是否啓動
        for(int i=0;i<3;i++){
            System.out.println(" main運行 --> " + i) ;
        }
        // 如下的輸出結果不肯定
        System.out.println("代碼執行以後 --> " + t.isAlive()) ;     // 判斷是否啓動
        
    }
};

  運行結果:

線程開始執行以前 --> false
線程開始執行以後 --> true
 main運行 --> 0
 main運行 --> 1
 main運行 --> 2
線程運行,i = 0
代碼執行以後 --> true
線程運行,i = 1
線程運行,i = 2

4,線程強制運行:join()

  能夠經過join()方法使得一個線程強制運行,線程強制運行期間,其餘線程沒法運行,必須等待此線程完成以後,才能夠繼續運行

package Thread1;
class MyThread implements Runnable{    // 實現Runnable接口
    public void run(){    // 覆寫run()方法
        for(int i=0;i<50;i++){
            System.out.println(Thread.currentThread().getName()
                    + "運行,i = " + i) ;    // 取得當前線程的名字
        }
    }
};
public class demo1{
    public static void main(String args[]){
        MyThread mt = new MyThread() ;    // 實例化Runnable子類對象
        Thread t = new Thread(mt,"線程");        // 實例化Thread對象
        t.start() ;    // 啓動線程
        for(int i=0;i<50;i++){
            if(i>10){
                try{
                    t.join() ;    // 線程強制運行
                }catch(InterruptedException e){}
            }
            System.out.println("Main線程運行 --> " + i) ;
        }
    }
};

運行結果:

線程運行,i = 0
Main線程運行 --> 0
線程運行,i = 1
Main線程運行 --> 1
線程運行,i = 2
Main線程運行 --> 2
線程運行,i = 3
線程運行,i = 4
線程運行,i = 5
線程運行,i = 6
線程運行,i = 7
線程運行,i = 8
線程運行,i = 9
Main線程運行 --> 3
線程運行,i = 10
Main線程運行 --> 4
線程運行,i = 11
線程運行,i = 12
線程運行,i = 13
Main線程運行 --> 5
線程運行,i = 14
Main線程運行 --> 6
線程運行,i = 15
線程運行,i = 16
線程運行,i = 17
線程運行,i = 18
線程運行,i = 19
Main線程運行 --> 7
線程運行,i = 20
Main線程運行 --> 8
線程運行,i = 21
Main線程運行 --> 9
線程運行,i = 22
Main線程運行 --> 10
線程運行,i = 23
線程運行,i = 24
線程運行,i = 25
線程運行,i = 26
線程運行,i = 27
線程運行,i = 28
線程運行,i = 29
線程運行,i = 30
線程運行,i = 31
線程運行,i = 32
線程運行,i = 33
線程運行,i = 34
線程運行,i = 35
線程運行,i = 36
線程運行,i = 37
線程運行,i = 38
線程運行,i = 39
線程運行,i = 40
線程運行,i = 41
線程運行,i = 42
線程運行,i = 43
線程運行,i = 44
線程運行,i = 45
線程運行,i = 46
線程運行,i = 47
線程運行,i = 48
線程運行,i = 49
Main線程運行 --> 11
Main線程運行 --> 12
Main線程運行 --> 13
Main線程運行 --> 14
Main線程運行 --> 15
Main線程運行 --> 16
Main線程運行 --> 17
Main線程運行 --> 18
Main線程運行 --> 19
Main線程運行 --> 20
Main線程運行 --> 21
Main線程運行 --> 22
Main線程運行 --> 23
Main線程運行 --> 24
Main線程運行 --> 25
Main線程運行 --> 26
Main線程運行 --> 27
Main線程運行 --> 28
Main線程運行 --> 29
Main線程運行 --> 30
Main線程運行 --> 31
Main線程運行 --> 32
Main線程運行 --> 33
Main線程運行 --> 34
Main線程運行 --> 35
Main線程運行 --> 36
Main線程運行 --> 37
Main線程運行 --> 38
Main線程運行 --> 39
Main線程運行 --> 40
Main線程運行 --> 41
Main線程運行 --> 42
Main線程運行 --> 43
Main線程運行 --> 44
Main線程運行 --> 45
Main線程運行 --> 46
Main線程運行 --> 47
Main線程運行 --> 48
Main線程運行 --> 49

3.5  線程的休眠

   在線程中容許一個線程進行暫時的休眠,直接使用Thread.sleep()方法便可。

  sleep定義格式:

public static void sleep(long milis,int nanos)
       throws InterruptedException

  首先,static,說明能夠由Thread類名稱調用,其次throws表示若是有異常要在調用此方法到處理異常

因此sleep()方法要有InterruptedException 異常處理,並且sleep()調用方法一般爲Thread.sleep(500) ;形式

  例子:

package Thread1;
class MyThread implements Runnable{    // 實現Runnable接口
    public void run(){    // 覆寫run()方法
        for(int i=0;i<50;i++){
            try{
                    Thread.sleep(500) ; // 線程休眠
            }catch(InterruptedException e){}
            System.out.println(Thread.currentThread().getName()
                    + "運行,i = " + i) ;    // 取得當前線程的名字
        }
    }
};
public class demo1{
    public static void main(String args[]){
        MyThread mt = new MyThread() ;    // 實例化Runnable子類對象
        Thread t = new Thread(mt,"線程");        // 實例化Thread對象
        t.start() ;    // 啓動線程
    }
};

會發現運行過程當中,線程名是一個個間隔必定時間出來的,這裏達到了休眠效果。

線程運行,i = 0
線程運行,i = 1
線程運行,i = 2
線程運行,i = 3
線程運行,i = 4
線程運行,i = 5
線程運行,i = 6
線程運行,i = 7
線程運行,i = 8
線程運行,i = 9
線程運行,i = 10
線程運行,i = 11
線程運行,i = 12
線程運行,i = 13
線程運行,i = 14
線程運行,i = 15
線程運行,i = 16
線程運行,i = 17
線程運行,i = 18
線程運行,i = 19
線程運行,i = 20
線程運行,i = 21
線程運行,i = 22
線程運行,i = 23
線程運行,i = 24
線程運行,i = 25
線程運行,i = 26
線程運行,i = 27
線程運行,i = 28
線程運行,i = 29
線程運行,i = 30
線程運行,i = 31
線程運行,i = 32
線程運行,i = 33
線程運行,i = 34
線程運行,i = 35
線程運行,i = 36
線程運行,i = 37
線程運行,i = 38
線程運行,i = 39
線程運行,i = 40
線程運行,i = 41
線程運行,i = 42
線程運行,i = 43
線程運行,i = 44
線程運行,i = 45
線程運行,i = 46
線程運行,i = 47
線程運行,i = 48
線程運行,i = 49

3.6 線程的中斷

  一個線程能夠被另外一個線程中斷其操做的狀態,使用 interrupt()方法完成。

package Thread1;
class MyThread implements Runnable{    // 實現Runnable接口
    public void run(){    // 覆寫run()方法
        System.out.println("一、進入run()方法") ;
        try{
                Thread.sleep(10000) ;    // 線程休眠10秒
                System.out.println("二、已經完成了休眠") ;
        }catch(InterruptedException e){
            System.out.println("三、休眠被終止") ;
        }
        System.out.println("四、run()方法正常結束") ;
    }
};
public class demo1{
    public static void main(String args[]){
        MyThread mt = new MyThread() ;    // 實例化Runnable子類對象
        Thread t = new Thread(mt,"線程");        // 實例化Thread對象
        t.start() ;    // 啓動線程
        try{
              Thread.sleep(2000) ; // 線程休眠2秒
        }catch(InterruptedException e){
            System.out.println("三、休眠被終止") ;
        }
        t.interrupt() ; // 中斷線程執行
    }
};

運行結果:

1、進入run()方法
3、休眠被終止
四、run()方法正常結束

  會看到,在1到3的時候會由於線程休眠2秒而卡頓了一下。

  可是,既然線程中斷了,那麼4,這句話不該該打出來的,所以要在3,線程被終止處添加一句話rutrun,表示返回調用處

package Thread1;
class MyThread implements Runnable{    // 實現Runnable接口
    public void run(){    // 覆寫run()方法
        System.out.println("一、進入run()方法") ;
        try{
                Thread.sleep(10000) ;    // 線程休眠10秒
                System.out.println("二、已經完成了休眠") ;
        }catch(InterruptedException e){
            System.out.println("三、休眠被終止") ;
            return ; // 返回調用處
        }
        System.out.println("四、run()方法正常結束") ;
    }
};
public class demo1{
    public static void main(String args[]){
        MyThread mt = new MyThread() ;    // 實例化Runnable子類對象
        Thread t = new Thread(mt,"線程");        // 實例化Thread對象
        t.start() ;    // 啓動線程
        try{
                Thread.sleep(2000) ;    // 線程休眠2秒
        }catch(InterruptedException e){
            System.out.println("三、休眠被終止") ;
        }
       t.interrupt() ; // 中斷線程執行
    }
};

運行結果:

1、進入run()方法
三、休眠被終止

3.7 後臺線程

  在Java中,只要一個線程沒有執行完(一個線程在運行),則整個Java的進程不會消失,因此此時能夠設置一個後臺線程,這樣即便java線程結束了,則後臺線程

依舊會繼續執行。要想實現這個操做,要使用setDaemon()方法完成。

   t.setDaemon(true) ; 

class MyThread implements Runnable{    // 實現Runnable接口
    public void run(){    // 覆寫run()方法
     int i=0; while(true){    //設置死循環,這樣來實現線程不斷運行,設置後臺運行。 System.out.println(Thread.currentThread().getName() + "在運行。"+i) ; } } }; public class ThreadDaemonDemo{ public static void main(String args[]){ MyThread mt = new MyThread() ; // 實例化Runnable子類對象 Thread t = new Thread(mt,"線程"); // 實例化Thread對象 t.setDaemon(true) ; // 此線程在後臺運行 t.start() ; // 啓動線程 } };

3.8線程的優先級

  獲取優先級的方法:getPriority();

  優先級分爲最低,最高,普通三個(Thread.MIN_PRIORITY,Thread.MAX_PRIORITY,Thread.NORM_PRIORITY),

設置優先級:

MyThread  t1=new MyThread();
Thread t3 = new Thread(t1,"線程C") ;//實例化線程對象
t3.setPriority(Thread.MIN_PRIORITY) ;//設置優先級爲最低

例子:

package Thread1;
class MyThread implements Runnable{    // 實現Runnable接口
    public void run(){    // 覆寫run()方法
        for(int i=0;i<5;i++){
            try{
                    Thread.sleep(500) ;    // 線程休眠
            }catch(InterruptedException e){}
            System.out.println(Thread.currentThread().getName()
                    + "運行,i = " + i) ;    // 取得當前線程的名字
        }
    }
};
public class demo1{
    public static void main(String args[]){
        Thread t1 = new Thread(new MyThread(),"線程A") ;    // 實例化線程對象
        Thread t2 = new Thread(new MyThread(),"線程B") ;    // 實例化線程對象
        Thread t3 = new Thread(new MyThread(),"線程C") ;    // 實例化線程對象
        t1.setPriority(Thread.MIN_PRIORITY) ;    // 優先級最低
        t2.setPriority(Thread.MAX_PRIORITY) ;    // 優先級最低
        t3.setPriority(Thread.NORM_PRIORITY) ;    // 優先級最低
        t1.start() ;    // 啓動線程
        t2.start() ;    // 啓動線程
        t3.start() ;    // 啓動線程
    }
};
 

運行結果:

線程B運行,i = 0
線程C運行,i = 0
線程A運行,i = 0
線程B運行,i = 1
線程C運行,i = 1
線程A運行,i = 1
線程B運行,i = 2
線程A運行,i = 2
線程C運行,i = 2
線程B運行,i = 3
線程C運行,i = 3
線程A運行,i = 3
線程B運行,i = 4
線程C運行,i = 4
線程A運行,i = 4

主方法的優先級

  主方法的優先級是NORM_PRIORITY.

package Thread1;
public class demo1{
    public static void main(String args[]){
        System.out.println("主方法的優先級:" + Thread.currentThread().getPriority()) ;    // 取得主方法的優先級
        System.out.println("MAX_PRIORITY = " + Thread.MAX_PRIORITY) ;
        System.out.println("NORM_PRIORITY = " + Thread.NORM_PRIORITY) ;
        System.out.println("MIN_PRIORITY = " + Thread.MIN_PRIORITY) ;
    }
};

運行結果:

主方法的優先級:5
MAX_PRIORITY = 10
NORM_PRIORITY = 5
MIN_PRIORITY = 1

  由此可知,主方法優先級是5,也就是普通優先級,並且主方法是一個線程對象。

3.9 線程的禮讓

  yield()方法實現線程的禮讓。

package Thread1;
class MyThread implements Runnable{    // 實現Runnable接口
    public void run(){    // 覆寫run()方法
        for(int i=0;i<5;i++){
            try{
                Thread.sleep(500) ;  //休眠一下
            }catch(Exception e){}
            System.out.println(Thread.currentThread().getName()
                    + "運行,i = " + i) ;    // 取得當前線程的名字
            if(i==2){
                System.out.print("線程禮讓:") ;
                Thread.currentThread().yield() ;    // 首先獲取當前線程,而後線程禮讓
            }
        }
    }
};
public class demo1{
    public static void main(String args[]){
        MyThread my = new MyThread() ;    // 實例化MyThread對象
        Thread t1 = new Thread(my,"線程A") ;
        Thread t2 = new Thread(my,"線程B") ;
        t1.start() ;
        t2.start() ;
    }
};

運行結果:

線程A運行,i = 0
線程B運行,i = 0
線程B運行,i = 1
線程A運行,i = 1
線程A運行,i = 2
線程禮讓:線程B運行,i = 2
線程禮讓:線程A運行,i = 3
線程B運行,i = 3
線程A運行,i = 4
線程B運行,i = 4
相關文章
相關標籤/搜索