Master-Worker模式是常用的並行模式,他的核心思想是,系統由兩類進程寫作工作:
Master進程和Worker進程。Master進程負責接收和分配任務,Worker進程負責處理子任務。當各個Worker進程將子任務處理完成後,將結果返回給Master進程,由Master進程進行彙總和歸納,從而得到系統的最終處理結果。
Master類
public class Master {
// 任務隊列
protected Queue<Object> workQueue = new ConcurrentLinkedQueue<Object>();
// worker進程隊列
protected Map<String, Thread> threadMap = new HashMap<String, Thread>();
// 子任務處理結果集
protected Map<String, Object> resultMap = new ConcurrentHashMap<String, Object>();
// 判斷是否所有的子任務都結束了
public boolean isComplete() {
for (Map.Entry<String, Thread> entry : threadMap.entrySet()) {
if (entry.getValue().getState() != Thread.State.TERMINATED) {
return false;
}
}
return true;
}
// Master的構造函數,需要一個Worker的進程邏輯和Worker的進程數量
public Master(Worker worker, int countWorker) {
worker.setWorkQueue(workQueue);
worker.setResultMap(resultMap);
for (int i = 0; i < countWorker; i++) {
threadMap.put(Integer.toString(i), new Thread(worker, Integer.toString(i)));
}
}
// 提交任務
public void submit(Object job) {
workQueue.add(job);
}
// 返回任務結果集
public Map<String, Object> getResultMap() {
return resultMap;
}
// 開始運行所有的worker進程,進行處理
public void execute() {
for (Map.Entry<String, Thread> entry : threadMap.entrySet()) {
entry.getValue().start();
}
}
}
Worker類
public class Worker implements Runnable {
//任務隊列,由於取得任務
protected Queue<Object> workQueue;
//子任務處理結果集
protected Map<String, Object> resultMap;
public void setWorkQueue(Queue<Object> workQueue) {
this.workQueue = workQueue;
}
public void setResultMap(Map<String, Object> resultMap) {
this.resultMap = resultMap;
}
//子任務的處理邏輯,在子類中實現具體的邏輯
public Object handle(Object input){
return input;
}
/**
*
* @see java.lang.Runnable#run()
*/
@Override
public void run() {
while(true){
Object input=workQueue.poll();
if(input==null){
break;
}else{
Object re=handle(input);
//將處理的結果寫入結果集中
resultMap.put(Integer.toString(input.hashCode()), re);
}
}
}
}
Worker具體實現類
public class PlusWorker extends Worker {
public Object handle(Object obj){
Integer i=(Integer) obj;
return i*i*i;
}
}
處理一個求0-n的立方和問題
public class TestMasterWorker {
/**
* @param args
*/
public static void main(String[] args) {
long begin=System.currentTimeMillis();
masterTest();
System.out.println((System.currentTimeMillis()-begin)/1000);
}
public static void masterTest() {
// 創建Master
Master master = new Master(new PlusWorker(), 5);
for (int i = 0; i < 100000; i++) {
master.submit(i);
}
master.execute();
int re = 0;
Map<String, Object> resultMap = master.getResultMap();
while (resultMap.size() > 0 || !master.isComplete()) {
Set<String> keys = resultMap.keySet();
String key = null;
for (String k : keys) {
key = k;
break;
}
Integer i = null;
if (key != null) {
i = (Integer) resultMap.get(key);
}
if (i != null) {
re += i;
}
if (key != null) {
resultMap.remove(key);// 移除已經被計算過的項
}
}
System.out.println("master" + re);
}
public static void testPlus() {
int re = 0;
for (int i = 0; i < 100000; i++) {
re += i * i * i;
}
System.out.println("testPlus:" + re);
}