Java線程池實例

線程池的作用:

線程池作用就是限制系統中執行線程的數量。
根據系統的環境情況,可以自動或手動設置線程數量,達到運行的最佳效果;少了浪費了系統資源,多了造成系統擁擠效率不高。用線程池控制線程數量,其他線程排隊等候。一個任務執行完畢,再從隊列的中取最前面的任務開始執行。若隊列中沒有等待進程,線程池的這一資源處於等待。當一個新任務需要運行時,如果線程池中有等待的工作線程,就可以開始運行了;否則進入等待隊列。



爲什麼要用線程池:

減少了創建和銷燬線程的次數,每個工作線程都可以被重複利用,可執行多個任務
可以根據系統的承受能力,調整線程池中工作線線程的數目,防止因爲因爲消耗過多的內存,而把服務器累趴下(每個線程需要大約1MB內存,線程開的越多,消耗的內存也就越大,最後死機)

線程池類


package com.tdt.impl.ls;

import java.util.LinkedList;

public class ThreadPool extends ThreadGroup {  
    private boolean isClosed = false;  //線程池是否關閉   
    private LinkedList workQueue;      //工作隊列  
    private static int threadPoolID = 1;  //線程池的id  
    public ThreadPool(int poolSize) {  //poolSize 表示線程池中的工作線程的數量  
 
        super(threadPoolID + "");      //指定ThreadGroup的名稱  
        setDaemon(true);               //繼承到的方法,設置是否守護線程池  
        workQueue = new LinkedList();  //創建工作隊列  
        for(int i = 0; i < poolSize; i++) {  
            new WorkThread(i).start();   //創建並啓動工作線程,線程池數量是多少就創建多少個工作線程  
        }  
    }  
      
    /** 向工作隊列中加入一個新任務,由工作線程去執行該任務*/  
    public synchronized void execute(Runnable task) {  
        if(isClosed) {  
            throw new IllegalStateException();  
        }  
        if(task != null) {  
            workQueue.add(task);//向隊列中加入一個任務  
            notify();           //喚醒一個正在getTask()方法中待任務的工作線程  
        }  
    }  
      
    /** 從工作隊列中取出一個任務,工作線程會調用此方法*/  
    private synchronized Runnable getTask(int threadid) throws InterruptedException {  
        while(workQueue.size() == 0) {  
            if(isClosed) return null;  
            System.out.println("工作線程"+threadid+"等待任務...");  
            wait();             //如果工作隊列中沒有任務,就等待任務  
        }  
        System.out.println("工作線程"+threadid+"開始執行任務...");  
        return (Runnable) workQueue.removeFirst(); //反回隊列中第一個元素,並從隊列中刪除  
    }  
      
    /** 關閉線程池 */  
    public synchronized void closePool() {  
        if(! isClosed) {  
            waitFinish();        //等待工作線程執行完畢  
            isClosed = true;  
            workQueue.clear();  //清空工作隊列  
            interrupt();        //中斷線程池中的所有的工作線程,此方法繼承自ThreadGroup類  
        }  
    }  
      
    /** 等待工作線程把所有任務執行完畢*/  
    public void waitFinish() {  
        synchronized (this) {  
            isClosed = true;  
            notifyAll();            //喚醒所有還在getTask()方法中等待任務的工作線程  
        }  
        Thread[] threads = new Thread[activeCount()]; //activeCount() 返回該線程組中活動線程的估計值。  
        int count = enumerate(threads); //enumerate()方法繼承自ThreadGroup類,根據活動線程的估計值獲得線程組中當前所有活動的工作線程  
        for(int i =0; i < count; i++) { //等待所有工作線程結束  
            try {  
                threads[i].join();  //等待工作線程結束  
            }catch(InterruptedException ex) {  
                ex.printStackTrace();  
            }  
        }  
    }  
 
    /**
     * 內部類,工作線程,負責從工作隊列中取出任務,並執行
     */  
    private class WorkThread extends Thread {  
        private int id;  
        public WorkThread(int id) {  
            //父類構造方法,將線程加入到當前ThreadPool線程組中  
            super(ThreadPool.this,id+"");  
            this.id =id;  
        }  
        public void run() {  
            while(! isInterrupted()) {  //isInterrupted()方法繼承自Thread類,判斷線程是否被中斷  
                Runnable task = null;  
                try {  
                    task = getTask(id);     //取出任務  
                }catch(InterruptedException ex) {  
                    ex.printStackTrace();  
                }  
                //如果getTask()返回null或者線程執行getTask()時被中斷,則結束此線程  
                if(task == null) return;  
                  
                try {  
                    task.run();  //運行任務  
                }catch(Throwable t) {  
                    t.printStackTrace();  
                }  
            }//  end while  
        }//  end run  
    }// end workThread  
}



2.測試類


package com.tdt.test;

public class ThreadPoolTest {

    public static void main(String[] args) throws InterruptedException {
        ThreadPool threadPool = new ThreadPool(3); // 創建一個有個3工作線程的線程池
        Thread.sleep(500); // 休眠500毫秒,以便讓線程池中的工作線程全部運行
        // 運行任務
        for (int i = 0; i <= 5; i++) { // 創建6個任務
            threadPool.execute(createTask(i));
        }
        threadPool.waitFinish(); // 等待所有任務執行完畢
        threadPool.closePool(); // 關閉線程池
    }

    private static Runnable createTask(final int taskID) {
        return new Runnable() {
            public void run() {
                //System.out.println("Task" + taskID + "開始");
                System.out.println("Hello world");
                //System.out.println("Task" + taskID + "結束");
            }
        };
    }
}





結果:

工作線程0等待任務...
工作線程1等待任務...
工作線程2等待任務...

工作線程0開始執行任務...
Hello world
工作線程0等待任務...

工作線程1開始執行任務...
Hello world
工作線程1等待任務...

工作線程2開始執行任務...
Hello world
工作線程2等待任務...

工作線程0開始執行任務...
Hello world
工作線程0等待任務...

工作線程1開始執行任務...
Hello world
工作線程1等待任務...

工作線程2開始執行任務...
Hello world
工作線程2等待任務...
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章