多線程的實現方法主要有三種分別是Thread類,Runnable接口和 callable接口,下面分別來說述一下三者的不一樣。java
首先是Thread類,須要被繼承以後才能實現,在實現的時候須要覆寫run()方法,可是在啓動的時候要用start()方法啓動。小程序
下面是一個賣票的小程序多線程
class MyThread extends Thread { //這是一個多線程的操做類 private int ticket = 10 ; @Override public void run(){ //覆寫run()方法,做爲線程主體操做方法 for(int x = 0 ;x <100; x ++) { if(this.ticket > 0){ System.out.println("賣票,ticket =" + this.ticket --) ; } } } } public class TestDemo { //主類 public static void main(String [] args){ //因爲MyThread類有start()方法,因此每個MyThread類對象就是一個線程對象,能夠直接啓動 MyThread mt1 = new MyThread() ; MyThread mt2 = new MyThread() ; MyThread mt3 = new MyThread() ; mt1.start(); mt2.start(); mt3.start(); } }
運行結果ide
Thread類實線多線程以後沒有共享資源,以賣票爲例,總共十張票,讓三我的去賣,若是每一個人都當本身有十張票,那麼總共就須要三十張票,這顯然不是咱們想要的結果。this
下面以Runnable接口來實現這個程序spa
class MyThread implements Runnable { //這是一個多線程的操做類 private int ticket = 10 ; @Override public void run(){ //覆寫run()方法,做爲線程主體操做方法 for(int x = 0 ;x <100; x ++) { if(this.ticket > 0){ System.out.println("賣票,ticket =" + this.ticket --) ; } } } } public class TestDemo { //主類 public static void main(String [] args){ //因爲MyThread類有start()方法,因此每個MyThread類對象就是一個線程對象,能夠直接啓動 MyThread mt = new MyThread(); new Thread(mt).start(); new Thread(mt).start(); new Thread(mt).start(); } }
運行結果線程
Runnable接口實現多線程就能達到資源共享的狀況,同時使用Runnable接口還能避免單繼承的侷限性。在Thread類中是繼承了Runnable接口,因此Runnable的多線程的實現,也是用到了Thread類中的start()方法。設計
一樣callable接口是爲了在java 1.5以後出現的,它是爲了解決Runnable接口操做完以後不能返回操做結果的缺陷而設計的code
import java.util.concurrent.Callable ; import java.util.concurrent.FutureTask ; class MyThread implements Callable<String> { //這是一個多線程的操做類 private int ticket = 10 ; @Override public String call() throws Exception { for(int x = 0 ;x <100; x ++) { if(this.ticket > 0){ System.out.println("賣票,ticket =" + this.ticket --) ; } } return "票已賣光" ; } } public class TestDemo { //主類 public static void main(String [] args) throws Exception { MyThread mt1 = new MyThread(); MyThread mt2 = new MyThread(); FutureTask<String> task1 = new FutureTask(mt1) ;//目的是爲了取回call()返回結果 FutureTask<String> task2 = new FutureTask(mt2) ;//目的是爲了取回call()返回結果 //FutureTask是Runnable接口子類,因此可使用Thread類的構造來接收task對象 new Thread(task1).start(); new Thread(task2).start(); //多線程執行完畢後能夠取得內容,依靠FutureTask的父接口Future中的get()方法完成 System.out.println("A線程返回的結果:" + task1.get()); System.out.println("B線程返回的結果:" + task1.get()); } }
因爲Callable接口實現多線程的方式比較麻煩,因此通常不用此操做,只作瞭解。對象