实现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 }
分类: Android