1. 模式概念
现在要生产一批小玩偶。小玩偶的制作分为四个步骤,第一要组装身体,第二要在身体上安装四肢和头部,第三,给组装完成的玩偶穿上一件漂亮的衣服,第四,就可以包装出货了。为了加快制作玩具的进度,我们不可能叫四个人同时加工一个玩具,因为这四个步骤有着严重的依赖关系。如果没有身体,就没有地方安装四肢,如果没有组装完成,就不能穿衣服,如果没有穿上衣服,就不能包装发货。因此,找四个人来做一个玩偶是毫无意义的。但是,如果你现在要制作的不是1只玩偶,而是1万只玩偶,那情况就不同了。你可以找四个人,第一个人只负责组装身体,完成后交给第二个人;第二个人只负责安装头部和四肢,交付第三人;第三人只负责穿衣服,并交付第四人;第四人只负责包装发货。这样所有人都可以一起工作,共同完成任务,而整个时间周期也能缩短到原来的1/4左右,这就是流水线的思想。一旦流水线满载,每次只需要一步(假设一个玩偶需要四步)就可以产生一个玩偶,
2. (B+C)*B/2
3. 程序代码
前置代码:
package com.john.learn.high.concurent.ch04.parallelline;
public class ParallelNode {
public double a;
public double b;
public String expression;
}
package com.john.learn.high.concurent.ch04.parallelline;
import java.text.MessageFormat;
import java.util.concurrent.BlockingQueue;
import java.util.concurrent.LinkedBlockingQueue;
public class ParallelFormulaQueue {
public static final BlockingQueue<ParallelNode> PlusQueue = new LinkedBlockingQueue<>();
public static final BlockingQueue<ParallelNode> MultipyQueue = new LinkedBlockingQueue<>();
public static final BlockingQueue<ParallelNode> DivideQueue = new LinkedBlockingQueue<>();
public static void add(ParallelNode parallelNode) {
PlusQueue.add(parallelNode);
}
public static void add(double a, double b) {
ParallelNode parallelNode = new ParallelNode();
parallelNode.a = a;
parallelNode.b = b;
PlusQueue.add(parallelNode);
}
P1: A=B+C
package com.john.learn.high.concurent.ch04.parallelline;
import java.text.MessageFormat;
import java.util.concurrent.BlockingQueue;
import java.util.concurrent.LinkedBlockingQueue;
public class Plus implements Runnable {
@Override
public void run() {
try {
while (true) {
ParallelNode parallelNode = ParallelFormulaQueue.PlusQueue.take();
if (parallelNode == null) {
continue;
}
parallelNode.expression = MessageFormat.format("({0}+{1})", parallelNode.a, parallelNode.b);
parallelNode.a = parallelNode.a + parallelNode.b;
ParallelFormulaQueue.MultipyQueue.add(parallelNode);
}
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
Thread.currentThread().interrupt();
}
}
}
}
P2: B=A*B
package com.john.learn.high.concurent.ch04.parallelline;
import java.text.MessageFormat;
import java.util.concurrent.BlockingQueue;
import java.util.concurrent.LinkedBlockingQueue;
public class Multipy implements Runnable {
@Override
public void run() {
try {
while (true) {
ParallelNode parallelNode = ParallelFormulaQueue.MultipyQueue.take();
if (parallelNode == null) {
continue;
}
parallelNode.expression = MessageFormat.format("{0}*{1}", parallelNode.expression, parallelNode.b);
parallelNode.a = parallelNode.a * parallelNode.b;
ParallelFormulaQueue.DivideQueue.add(parallelNode);
}
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
Thread.currentThread().interrupt();
}
}
}
P3: D=D/2
package com.john.learn.high.concurent.ch04.parallelline;
import java.text.MessageFormat;
import java.util.concurrent.BlockingQueue;
import java.util.concurrent.LinkedBlockingQueue;
public class Divide implements Runnable {
@Override
public void run() {
try {
while (true) {
ParallelNode parallelNode = ParallelFormulaQueue.DivideQueue.take();
if (parallelNode == null) {
continue;
}
System.out.println(MessageFormat.format("{0}/2={1}", parallelNode.expression, parallelNode.a / 2));
}
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
Thread.currentThread().interrupt();
}
}
}
package com.john.learn.high.concurent.ch04.parallelline;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
public class ParallelMain {
public static void main(String[] args) {
ExecutorService executorService = Executors.newCachedThreadPool();
executorService.submit(new Plus());
executorService.submit(new Multipy());
executorService.submit(new Divide());
//(B+C)*B/2
for(int i=0;i<1000;i++) {
for(int j=0;j<1000;j++) {
ParallelFormulaQueue.add(i, j);
}
}
executorService.shutdownNow();
}
}