1.定义
Master-Worker模式是常用的并行设计模式。它的核心思想是,系统有两个进程协议工作:Master进程和Worker进程。Master进程负责接收和分配任务,Worker进程负责处理子任务。当各个Worker进程将子任务处理完后,将结果返回给Master进程,由Master进行归纳和汇总,从而得到系统结果。
2.实现
2.1定义worker基类
package com.ldzn.concurrency.designpattern.masterworker;
import java.util.HashMap;
import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.ConcurrentLinkedQueue;
/**
* @ClassName : BaseWorker
* @Description:
* @Author: liulianglin
* @Date: 2019/12/12 17:45
* @Version : 1.0
*/
public class BaseWorker<T> implements Runnable{
/**
1.定义一个承载任务的集合
*/
private ConcurrentLinkedQueue<MTask> taskQueue = new ConcurrentLinkedQueue<>();
/**
* 2. 定义一个承载所有worker执行结果的容器
* ConcurrentHashMap
*/
private ConcurrentHashMap<Integer, T> resultMap = new ConcurrentHashMap<>();
public void setTaskQueue(ConcurrentLinkedQueue<MTask> taskQueue){
this.taskQueue = taskQueue;
}
public void setResultMap(ConcurrentHashMap<Integer, T> resultMap){
this.resultMap = resultMap;
}
@Override
public void run() {
//循环处理任务
while(true){
MTask task = this.taskQueue.poll();
if (null == task){
System.out.println("取出任务为空");
break;
}
System.out.println("从任务队列中取出一个任务,task="+task.getTaskName());
//任务处理
System.out.println("开始处理任务"+task.getTaskName());
T result = null;
try {
result = handleTask(task);
} catch (InterruptedException e) {
e.printStackTrace();
}
this.resultMap.put(task.getTaskId(), result);
}
}
/**
* 处理任务,由子类具体负责实现
* @param task
* @return
*/
public T handleTask(MTask task) throws InterruptedException {
return null;
}
}
2.2定义一个worker实现类
package com.ldzn.concurrency.designpattern.masterworker;
/**
* @ClassName : MWorker1
* @Description:
* @Author: liulianglin
* @Date: 2019/12/12 18:02
* @Version : 1.0
*/
public class MWorker1 extends BaseWorker<MResult> {
@Override
public MResult handleTask(MTask task) throws InterruptedException {
System.out.println("进入worker1,开始处理taskId="+task.getTaskId()+ ", tasskName="+task.getTaskName());
if (null == task){
System.out.println("输入参数--任务为空");
return null;
}
Thread.sleep(1000);
MResult result = new MResult();
result.setTaskId(task.getTaskId());
result.setResult("woker1-----成功");
System.out.println(task.getTaskName()+"执行完毕, 返回结果");
return result;
}
}
2.3定义一个Master
package com.ldzn.concurrency.designpattern.masterworker;
import com.sun.tools.javac.api.MultiTaskListener;
import java.util.HashMap;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.ConcurrentLinkedQueue;
/**
* @ClassName : MyMaster
* @Description:
* @Author: liulianglin
* @Date: 2019/12/12 17:45
* @Version : 1.0
*/
public class MyMaster<T> {
/**
1.定义一个承载任务的集合
*/
private ConcurrentLinkedQueue<MTask> taskQueue = new ConcurrentLinkedQueue<>();
/**
* 2.定义一个承载worker的集合
*/
private HashMap<String, Thread> workersMap = new HashMap<>();
/**
* 3. 定义一个承载所有worker执行结果的容器
* ConcurrentHashMap
*
* key:taskId
* value: 任务结果
*/
private ConcurrentHashMap<Integer, T> resultMap = new ConcurrentHashMap<>();
public MyMaster(BaseWorker worker, int workerCount){
worker.setTaskQueue(this.taskQueue);
worker.setResultMap(this.resultMap);
for (int i=0; i<workerCount; i++){
workersMap.put("子工作线程"+i, new Thread(worker));
}
}
/**
* 提交任务
*/
public void submitTask(MTask mtask){
taskQueue.add(mtask);
}
/**
* 任务执行
*/
public void executeTask(){
//遍历所有workers,顺序启动所有worker线程
for (Map.Entry<String, Thread> worker : workersMap.entrySet()){
worker.getValue().start();
}
}
/**
* 判断所有的worker是否都执行完毕
*/
public boolean isAllCompleted(){
for (Map.Entry<String, Thread> worker : workersMap.entrySet()){
if (worker.getValue().getState() != Thread.State.TERMINATED){
return false;
}
}
return true;
}
/**
* 计算最终结果
*/
public String getResult(){
String result = null;
for (Map.Entry<Integer, T> worker : resultMap.entrySet()){
result += worker.getValue().toString();
result += "\n";
}
return result;
}
}
2.4定义一个任务类
package com.ldzn.concurrency.designpattern.masterworker;
/**
* @ClassName : MTask
* @Description:
* @Author: liulianglin
* @Date: 2019/12/12 17:46
* @Version : 1.0
*/
public class MTask {
private int taskId;
private String taskName;
public int getTaskId() {
return taskId;
}
public void setTaskId(int taskId) {
this.taskId = taskId;
}
public String getTaskName() {
return taskName;
}
public void setTaskName(String taskName) {
this.taskName = taskName;
}
@Override
public String toString() {
return "MTask{" +
"taskId=" + taskId +
", taskName='" + taskName + '\'' +
'}';
}
}
2.5定义一个结果类
package com.ldzn.concurrency.designpattern.masterworker;
/**
* @ClassName : MResult
* @Description:
* @Author: liulianglin
* @Date: 2019/12/12 18:04
* @Version : 1.0
*/
public class MResult {
private int taskId;
private String result;
public int getTaskId() {
return taskId;
}
public void setTaskId(int taskId) {
this.taskId = taskId;
}
public String getResult() {
return result;
}
public void setResult(String result) {
this.result = result;
}
@Override
public String toString() {
return "MResult{" +
"taskId=" + taskId +
", result='" + result + '\'' +
'}';
}
}
2.6最后编写一个测试类
package com.ldzn.concurrency.designpattern.masterworker;
/**
* @ClassName : MasterWokerTest
* @Description: MasterWoker模式
* @Author: liulianglin
* @Date: 2019/12/12 10:56
* @Version : 1.0
*/
public class MasterWokerTest {
public static void main(String[] args) {
MyMaster master = new MyMaster(new MWorker1(), 4);
//构造4个任务
for (int i = 0; i <= 4; i++){
MTask task = new MTask();
task.setTaskId(i);
task.setTaskName("任务"+i);
master.submitTask(task);
}
//执行
master.executeTask();
//记录时间
long startTime = System.currentTimeMillis();
while (true) {
if (master.isAllCompleted()) {
//记录时间
long endTime = System.currentTimeMillis();
System.out.println("\n最终执行结果-----" + master.getResult());
System.out.println("执行耗时=" + (endTime - startTime));
break;
}
}
}
}