Java多線程

PART.1  通過Thread實現多線程<?xml:namespace prefix = o ns = "urn:schemas-microsoft-com:office:office" />

 

1. Thread

 

getID()

獲取線程ID

getName(), setName()

獲取和設置線程名。

getPriority(),  setPriority()

獲取和設置線程優先級。

getState()

獲取線程狀態。

getThreadGroup()

獲取線程所在的線程組。

isAlive()

獲取線程是否已經啓動並且沒有終止。

isDaemon(), setDaemon()

獲取和設置線程是否爲守護線程。

isInterrupted()

獲取線程是否被中斷。

 

start()

開始線程。

join()

等待指定線程中終止。

interrupt()

中斷線程

 

靜態方法

currentThread()

獲取當前線程。

sleep()

使當前線程休眠指定的時間。

yield()

使當前線程暫停執行,讓其它等待的線程執行。

interrupted()

獲取當前線程是否被中斷。

 

 

 

2. 通過Thread實現多線程

1. 通過繼承Thread類並覆蓋Threadrun()方法創建一個新的線程類。

2. 使用該線程類創建線程對象。

  1. public class ThreadTest
  2. {
  3.     public static void main(String[] args) throws Exception
  4.     {
  5.         TestThread th = new TestThread("thread 1");
  6.         th.start();
  7.         th.join();
  8.         System.out.println("'main' ended.");
  9.     }
  10.     
  11.     private static class TestThread extends Thread
  12.     {
  13.         public TestThread(String threadName)
  14.         {
  15.             super(threadName);
  16.         }
  17.         
  18.         @Override
  19.         public void run()
  20.         {
  21.             String thName = Thread.currentThread().getName();
  22.             System.out.printf("'%s' started. /n", thName);
  23.             for (int i = 0; i < 10; i++)
  24.             {
  25.                 System.out.println(i);
  26.             }
  27.             System.out.printf("'%s' ended. /n", thName);
  28.         }
  29.     }
  30. }

 

3. 通過Runnable實現多線程

1. 創建一個Runnable接口的實現類(實現run()方法)。

2. 通過Thread類包含Runnable的構造方法創建線程對象。

  Thread(Runnable target)

  Thread(ThreadGroup group, Runnable target)

  ThreadGroup group, Runnable target, String name)

  1. public class RunnableTest
  2. {
  3.     public static void main(String[] args) throws Exception
  4.     {
  5.         Thread th = new Thread(new TestRunnable(), "thread 1");
  6.         th.start();
  7.         th.join();
  8.         System.out.println("'main' ended.");
  9.     }
  10.     
  11.     private static class TestRunnable implements Runnable
  12.     {
  13.         @Override
  14.         public void run()
  15.         {
  16.             String thName = Thread.currentThread().getName();
  17.             System.out.printf("'%s' started. /n", thName);
  18.             for (int i = 0; i < 10; i++)
  19.             {
  20.                 System.out.println(i);
  21.             }
  22.             System.out.printf("'%s' ended. /n", thName);
  23.         }
  24.     }
  25. }

 

4. ThreadGroup

activeCount()

獲取線程組中正在執行的線程數量。

activeGroupCount()

獲取線程組中正在執行的線程組數量。

getMaxPriority(), setMaxPriority()

獲取和設置最大優先級

getName()

獲取線程組的名稱。

getParent()

獲取父線程組

interrupt()

中斷線程組中的所有線程。

isDaemon(), setDaemon()

獲取和設置線程組是否爲守護線程。

parentOf(ThreadGroup)

判斷線程組是否包含於指定線程組中。

 

 

5. 通過ThreadGroup管理線程

在創建線程對象時,通過包含ThreadGroup的構造方法創建,將線程加入指定線程組

  Thread(ThreadGroup group, Runnable target)

  Thread(ThreadGroup group, Runnable target, String name)

  Thread(ThreadGroup group, String name)

  1. public class ThreadGroupTest
  2. {
  3.     
  4.     public static void main(String[] args) throws Exception
  5.     {
  6.         // 創建線程組對象。
  7.         ThreadGroup tg = new ThreadGroup("group 1");
  8.         
  9.         // 向線程組中加入10個線程。
  10.         for (int i = 0; i < 10; i++)
  11.         {
  12.             Thread th = new Thread(tg, new TestRunnable(), "thread " + i);
  13.             th.start();
  14.         }
  15.         
  16.         // 等待2秒。
  17.         Thread.sleep(2000);
  18.         
  19.         // 中斷所有線程。
  20.         tg.interrupt();
  21.         
  22.         // 輸出
  23.         System.out.println(tg.activeCount());
  24.     }
  25.     
  26.     private static class TestRunnable implements Runnable
  27.     {
  28.         @Override
  29.         public void run()
  30.         {
  31.             String thName = Thread.currentThread().getName();
  32.             System.out.printf("'%s' started. /n", thName);
  33.             while (!Thread.currentThread().isInterrupted())
  34.             {
  35.             }
  36.             System.out.printf("'%s' ended. /n", thName);
  37.         }
  38.     }
  39. }

PART.2  通過CallableFutureTask實現異步調用

 

1. Callable<V>

Ø  V爲返回值的類型。

Ø  實現Callable接口需實現call方法。

Ø  Runnablerun方法相比,call方法具有返回值V和異常聲明。

 

 

2. FutureTask<V>

V爲返回值得類型。

cancel()

取消執行。

get()

阻塞獲取執行結果。

get(long, TimeUnit)

指定阻塞的最長時間,獲取執行結果。

isCancelled()

獲取是否被取消。

isDone()

獲取是否完成。

run()

開始執行。

 

 

3. 通過CallableFutureTask異步執行

1. 創建一個Callable<V>的實現類。

2. 創建FutureTask<V>對象。

3. 執行創建的FutureTask對象。(run方法)

4. 通過FutureTask對象獲取結果。(get方法)

  1. import java.util.concurrent.Callable;
  2. import java.util.concurrent.ExecutionException;
  3. import java.util.concurrent.FutureTask;
  4. public class FutureTaskTest
  5. {
  6.     public static void main(String[] args)
  7.     {
  8.         FutureTask<Integer> ct = null;
  9.         
  10.         ct = new FutureTask<Integer>(new TestCallable());
  11.         ct.run();
  12.         
  13.         try
  14.         {
  15.             int ret = ct.get();
  16.             System.out.println(ret);
  17.         }
  18.         catch (InterruptedException e)
  19.         {
  20.             // ct.get() 時線程被中斷。 
  21.             e.printStackTrace();
  22.         }
  23.         catch (ExecutionException e)
  24.         {
  25.             // Callable在執行時出現異常。
  26.             e.printStackTrace();
  27.         }
  28.     }
  29.     private static class TestCallable implements Callable<Integer>
  30.     {
  31.         @Override
  32.         public Integer call() throws Exception
  33.         {
  34.             double i = Math.random() * 100;
  35.             return (int)i;
  36.         }
  37.     }
  38. }

4.處理FutureTask執行時發生的異常

  1. import java.util.concurrent.Callable;
  2. import java.util.concurrent.ExecutionException;
  3. import java.util.concurrent.FutureTask;
  4. public class FutureTaskExceptionTest
  5. {
  6.     public static void main(String[] args)
  7.     {
  8.         FutureTask<Integer> ct = null;
  9.         
  10.         ct = new FutureTask<Integer>(new TestCallable());
  11.         ct.run();
  12.         
  13.         try
  14.         {
  15.             int ret = ct.get();
  16.             System.out.println(ret);
  17.         }
  18.         catch (InterruptedException e)
  19.         {
  20.             // ct.get() 時線程被中斷。 
  21.             e.printStackTrace();
  22.         }
  23.         catch (ExecutionException e)
  24.         {
  25.             // Callable在執行時出現異常。
  26.             System.out.println(e.getCause().getMessage());
  27.             System.out.println(e.getMessage());
  28.         }
  29.     }
  30.     private static class TestCallable implements Callable<Integer>
  31.     {
  32.         @Override
  33.         public Integer call() throws Exception
  34.         {
  35.             throw new Exception("An test exception.");
  36.         }
  37.     }
  38. }

PART.3  通過ExecutorService實現多線程

 

1. ExecutorService

awaitTermination

等待所有任務結束。

invokeAll

執行集合中的所有任務,返回所有Future。該方法將等待所有任務結束或指定的時間。

invokeAny

執行集合中的一個任務,返回該任務得返回值。

isShutdown

獲取ExecutorService是否被shutdown

isTerminated

獲取是否所有任務已經結束。

Shutdown

等待所有正在執行的任務結束。將沒有執行的任務返回。不執行後新的任務。

shutdownNow

中斷正在執行的任務。返回沒有執行的任務。

submit

提交一個任務並開始執行。

 

2. 創建ExecutorService

Executors.newCachedThreadPool

Executors.newFixedThreadPool

Executors.newScheduledThreadPool

Executors.newSingleThreadExecutor

Executors.newSingleThreadScheduledExecutor

 

 

3. 通過ExecutorService實現多線程

1. 創建ExecutorService對象。

2. ExecutorServices對象提交任務。

3. 獲得結果。

  1. import java.util.ArrayList;
  2. import java.util.List;
  3. import java.util.concurrent.Callable;
  4. import java.util.concurrent.ExecutorService;
  5. import java.util.concurrent.Executors;
  6. import java.util.concurrent.Future;
  7. public class ExecutorServiceTest
  8. {
  9.     public static void main(String[] args) throws Exception
  10.     {
  11.         ExecutorService es = Executors.newCachedThreadPool();
  12.         
  13.         // 創建10個任務,將這些任務交由ExecutorService執行,保存這些任務的Future到List。
  14.         List<Future<Integer>> fs = new ArrayList<Future<Integer>>(10); 
  15.         for (int i = 0; i < 10; i++)
  16.         {
  17.             TestCallable t = new TestCallable();
  18.             Future<Integer> f = es.submit(t);
  19.             fs.add(f);
  20.         }
  21.         
  22.         // 等待執行結束。
  23.         Thread.sleep(1000);
  24.         
  25.         // 輸出執行結果。
  26.         for (Future<Integer> f : fs)
  27.         {
  28.             System.out.println(f.get());
  29.         }
  30.         
  31.         // 關閉ExecutorService。
  32.         es.shutdown();
  33.     }
  34.     
  35.     private static class TestCallable implements Callable<Integer>
  36.     {
  37.         @Override
  38.         public Integer call() throws Exception
  39.         {
  40.             double ret = Math.random() * 100;
  41.             return (int)ret;
  42.         }
  43.     }
  44. }

4. 關閉ExecutorService

shutdown()                等待任務結束

shutdownNow()       中斷任務

 
  1. import java.util.concurrent.Callable;
  2. import java.util.concurrent.ExecutorService;
  3. import java.util.concurrent.Executors;
  4. public class ExecutorServiceShutdownTest
  5. {
  6.     public static void main(String[] args) throws Exception
  7.     {
  8.         // PART 1  測試shutdownNow()。
  9.         System.out.println("----- PART 1");
  10.         
  11.         // 創建ExecutorService。
  12.         ExecutorService es = Executors.newCachedThreadPool();
  13.         
  14.         // 開始10個任務。
  15.         System.out.println("----- Start all tasks...");
  16.         for (int i = 0; i < 10; i++)
  17.         {
  18.             TestCallable task = new TestCallable("task " + i);
  19.             es.submit(task);
  20.         }
  21.         
  22.         // 等待5秒。在此期間可能有任務結束。
  23.         System.out.println("----- Wait for 5 seconds.");
  24.         Thread.sleep(5000);
  25.         
  26.         // 結束所有任務。
  27.         System.out.println("----- Shutdown all tasks now.");
  28.         es.shutdownNow();
  29.         
  30.         System.out.println("----- End of PART 1");
  31.         Thread.sleep(1000);
  32.         
  33.         // 測試shutdown()。 
  34.         System.out.println("----- PART 2");
  35.         Thread.sleep(1000);
  36.         // 創建ExecutorService。
  37.         es = Executors.newCachedThreadPool();
  38.         
  39.         // 開始10個任務。
  40.         System.out.println("----- Start all tasks...");
  41.         for (int i = 0; i < 10; i++)
  42.         {
  43.             TestCallable task = new TestCallable("task " + i);
  44.             es.submit(task);
  45.         }
  46.         // 等待5秒。在此期間可能有任務結束。
  47.         System.out.println("----- Wait for 5 seconds.");
  48.         Thread.sleep(5000);
  49.         
  50.         // 結束所有任務。
  51.         System.out.println("----- Shutdown all tasks.");
  52.         es.shutdown();
  53.     
  54.         System.out.println("----- End of main.");
  55.     }
  56.     private static class TestCallable implements Callable<Void>
  57.     {
  58.         private String name;
  59.         
  60.         public TestCallable(String name)
  61.         {
  62.             this.name = name;
  63.         }
  64.         
  65.         @Override
  66.         public Void call() throws Exception
  67.         {
  68.             System.out.printf("'%s' started. /n", name);
  69.             
  70.             // 等待3 - 12秒。
  71.             try
  72.             {
  73.                 
  74.                 int w = (int)(Math.random() * 10 + 3);
  75.                 Thread.sleep(w*1000);
  76.             }
  77.             catch (InterruptedException e)
  78.             {
  79.                 System.out.printf("'%s' interrupted. /n", name);
  80.             }
  81.             
  82.             System.out.printf("'%s' ended. /n", name);
  83.             return null;
  84.         }
  85.     }
  86. }

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章