自己动手实现JAVA线程池

  线程池,只听过,没见过也没用过。项目中因为牵扯到图片下载,所以借此机会来学习一下这方面的知识。

 

  线程池的知识,我在这里就不进行总结了,网上是很多的,我这边文章主要就是总结一下自己写的线程池代码。

  首先先说一下我的思路。线程池嘛,肯定是一个对多个线程引用的一个对象,有添加任务、激活线程去完成任务、关闭等功能。工作线程需要保证完成一项任务之后不结束,那么需要run方法中是一个类似于死循环的循环,循环的出口是线程池关闭的标志。但是当线程池中没有任务时,工作线程不能让这个循环进去下去,这样实际上是增加的CPU负担,所以需要使工作线程在没有工作时处于等待状态(wait)。工作线程每次接收到任务时,就需要做指定的任务,因此需要一个任务接口,工作线程接收到任务则调用这个接口中的指定方法即可。

  

  线程池类

  1 package my.java.threadpool;
  2 
  3 import java.util.Collections;
  4 import java.util.LinkedList;
  5 import java.util.List;
  6 
  7 public class ThreadPool
  8 {
  9     private final int MAX_COUNT = 3;
 10     private WorkThread worker[] = new WorkThread[MAX_COUNT];
 11 
 12     private List<Task> taskList = Collections.synchronizedList(new LinkedList<Task>());
 13 
 14     private boolean isRun = false;
 15 
 16     private int length = 0;
 17     private boolean isShowLog;
 18 
 19     private static ThreadPool httpClient = new ThreadPool();
 20 
 21     private ThreadPool()
 22     {
 23         isRun = true;
 24         for (int i = 0; i < MAX_COUNT; i++)
 25         {
 26             worker[i] = new WorkThread(this, "工作线程" + i + "号");
 27 
 28             worker[i].start();
 29         }
 30     }
 31 
 32     public static ThreadPool getInstance()
 33     {
 34         return httpClient;
 35     }
 36 
 37     /**
 38      * 在线程池中添加新的任务
 39      * 
 40      * @param object
 41      *            操作线程可能需要的数据
 42      */
 43     public void addToThreadPool(Task run)
 44     {
 45         synchronized (taskList)
 46         {
 47             taskList.add(run);
 48             taskList.notify();
 49         }
 50     }
 51 
 52     public void closeTheadPool()
 53     {
 54         printLog("开始关闭线程池");
 55         isRun = false;
 56         synchronized (taskList)
 57         {
 58             taskList.clear();
 59 
 60             for (int i = 0; i < MAX_COUNT; i++)
 61             {
 62                 printLog("线程池关闭" + worker[i].getName());
 63                 worker[i].stopWorkThread();
 64             }
 65 
 66             taskList.notifyAll();
 67         }
 68     }
 69 
 70     public String getTaskLength()
 71     {
 72         return "已经运行" + length + "个任务";
 73     }
 74 
 75     public String getThreadPoolInfo()
 76     {
 77         StringBuffer sb = new StringBuffer();
 78         sb.append("线程池中共有" + MAX_COUNT + "个线程\n");
 79         for (int i = 0; i < MAX_COUNT; i++)
 80         {
 81             sb.append(worker[i].getName()).append("当前处于").append(worker[i].getState()).append("状态\n");
 82         }
 83         return sb.toString();
 84     }
 85 
 86     public Task getTask()
 87     {
 88         Task run = null;
 89         if (isRun)
 90         {
 91             synchronized (taskList)
 92             {
 93                 while (taskList.isEmpty())
 94                 {
 95                     try
 96                     {
 97                         printLog(Thread.currentThread().getName() + "暂停");
 98                         taskList.wait();
 99                     }
100                     catch (InterruptedException e)
101                     {
102                         e.printStackTrace();
103                     }
104 
105                     if (!isRun)
106                         return null;
107                 }
108                 run = taskList.remove(0);
109                 length++;
110             }
111         }
112         return run;
113     }
114 
115     public void printLog(String log)
116     {
117         if (isShowLog)
118         {
119             System.out.println(log);
120         }
121     }
122 }

  工作线程类

 1 package my.java.threadpool;
 2 
 3 public class WorkThread extends Thread
 4 {
 5     private boolean isRun;
 6     private ThreadPool pool;
 7     private boolean isShowLog;
 8 
 9     public WorkThread(ThreadPool pool, String name)
10     {
11         isRun = true;
12         this.pool = pool;
13         setName(name);
14     }
15 
16     @Override
17     public void run()
18     {
19         printLog(getName() + "开启");
20         while (isRun)
21         {
22             Task run = pool.getTask();
23 
24             if (null == run)
25             {
26                 continue;
27             }
28             printLog(getName() + "开始工作");
29             try
30             {
31                 run.run();
32             }
33             catch (Exception e)
34             {
35                 e.printStackTrace();
36             }
37             printLog(getName() + "完成工作");
38         }
39 
40         printLog(getName() + "关闭");
41     }
42 
43     public void stopWorkThread()
44     {
45         isRun = false;
46     }
47     
48     public void printLog(String log)
49     {
50         if (isShowLog)
51         {
52             System.out.println(log);
53         }
54     }
55 }

  工作接口

1 package my.java.threadpool;
2 
3 public interface Task
4 {
5     /**
6      * 耗时操作,也就是工作线程具体要做的内容
7      */
8     public void run();
9 }

  测试类

 1 package my.java.threadpool;
 2 
 3 import java.util.Random;
 4 
 5 public class Test
 6 {
 7     public static void main(String[] args) throws InterruptedException
 8     {
 9 
10         ThreadPool pool = ThreadPool.getInstance();
11 
12         System.out.println("开始添加任务");
13 
14         for (int i = 0; i < 50; i++)
15         {
16             Task run = new Task()
17             {
18                 @Override
19                 public void run()
20                 {
21                     try
22                     {
23                         Thread.sleep(new Random().nextInt(5) * 1000);
24                     }
25                     catch (InterruptedException e)
26                     {
27                         e.printStackTrace();
28                     }
29                 }
30             };
31             pool.addToThreadPool(run);
32         }
33 
34         System.out.println(pool.getThreadPoolInfo());
35         // Thread.sleep(100 * 1000);
36         pool.closeTheadPool();
37     }
38 }

 

posted @ 2013-05-15 17:38  猪圈里的猪  阅读(1387)  评论(0编辑  收藏  举报