Java8（6）：使用并行流

mizhoux

``````public long recursiveFibonacci(int n) {
if (n < 2) {
return 1;
}

return recursiveFibonacci(n - 1) + recursiveFibonacci(n - 2);
}``````

``````public long iterativeFibonacci(int n) {
long n1 = 1, n2 = 1;
long fi = 2; // n1 + n2

for (int i = 2; i <= n; i++) {
fi = n1 + n2;
n1 = n2;
n2 = fi;
}

return fi;
}``````

=>

f0f1 都是 1 —— 很明显我们可以对 进行并行计算。

``````public class Matrix {

/**
* 左上角的值
*/
public final BigInteger a;
/**
* 右上角的值
*/
public final BigInteger b;
/**
* 左下角的值
*/
public final BigInteger c;
/**
* 右下角的值
*/
public final BigInteger d;

public Matrix(int a, int b, int c, int d) {
this(BigInteger.valueOf(a), BigInteger.valueOf(b),
BigInteger.valueOf(c), BigInteger.valueOf(d));
}

public Matrix(BigInteger a, BigInteger b, BigInteger c, BigInteger d) {
this.a = a;
this.b = b;
this.c = c;
this.d = d;
}

/**
* multiply
*
* @param m multiplier
* @return
*/
public Matrix mul(Matrix m) {
return new Matrix(
}

/**
* power of exponent
*
* @param exponent
* @return
*/
public Matrix pow(int exponent) {
Matrix matrix = this.copy();

for (int i = 1; i < exponent; i++) {
matrix = matrix.mul(this);
}

return matrix;
}

public Matrix copy() {
return new Matrix(a, b, c, d);
}

}``````

``````public static void main(String[] args) throws Exception {
final int ITEM_NUM = 500000; // 计算斐波那契数列的第 ITEM_NUM 项

System.out.println("开始迭代计算...");
long begin = System.nanoTime();

BigInteger fi1 = iterativeFibonacci(ITEM_NUM);

long end = System.nanoTime();
double time = (end - begin) / 1E9;
System.out.printf("迭代计算用时: %.3f\n\n", time);

/* ------------------------------ */
System.out.println("开始并行计算...");
begin = System.nanoTime();

BigInteger fi2 = parallelFibonacci(ITEM_NUM, 1);

end = System.nanoTime();
time = (end - begin) / 1E9;
System.out.printf("并行计算用时: %.3f\n\n", time);

System.out.println("fi1 == fi2：" + (fi1.equals(fi2)));
}

static BigInteger iterativeFibonacci(int n) {
BigInteger n1 = BigInteger.ONE;
BigInteger n2 = BigInteger.ONE;
BigInteger fi = BigInteger.valueOf(2); // n1 + n2

for (int i = 2; i <= n; i++) {
n1 = n2;
n2 = fi;
}

return fi;
}

static BigInteger parallelFibonacci(int itemNum, int threadNum) throws Exception {
final Matrix matrix = new Matrix(1, 1, 1, 0);
final Matrix primary = new Matrix(1, 0, 1, 0); // (f0, 0; f1, 0)

for (int i = 0; i < threadNum; i++) {
if (i < threadNum - 1) {
// 为了简洁，使用 Lambda 表达式替代要实现 Callable<Matrix> 的匿名内部类
} else {
}
}

Matrix result = primary.copy();
for (Future<Matrix> future : futures) { // (matrix ^ n) * (f0, 0; f1, 0)
result = result.mul(future.get());
}

return result.c;
}``````

``BigInteger fi2 = parallelFibonacci(ITEM_NUM, 10); // 10 线程并行计算``

``````static BigInteger streamFibonacci(int itemNum, int threadNum) {
final Matrix matrix = new Matrix(1, 1, 1, 0);
final Matrix primary = new Matrix(1, 0, 1, 0);

// 流式 API
.parallel()                     // 使流并行化
.mapToObj(w -> matrix.pow(w))   // map    ->  mN = matrix ^ workload
.reduce((m1, m2) -> m1.mul(m2)) // reduce ->  m = m1 * m2 * ... * mN
.map(m -> m.mul(primary))       // map    ->  m = m * primary
.get().c;                       // get    ->  m.c
}``````

``````public static void main(String[] args) throws Exception {
...

/* ------------------------------ */
System.out.println("开始流式并行计算...");
begin = System.nanoTime();

BigInteger fi3 = streamFibonacci(ITEM_NUM, 10);

end = System.nanoTime();
time = (end - begin) / 1E9;
System.out.printf("流式并行计算用时: %.3f\n\n", time);

System.out.println("fi1 == fi2：" + (fi1.equals(fi2)));
System.out.println("fi1 == fi3：" + (fi1.equals(fi3)));
}``````

``````BigInteger fi2 = parallelFibonacci(ITEM_NUM, 32);

...

BigInteger fi3 = streamFibonacci(ITEM_NUM, 32);``````

Java Follower
Java 平台是博大精深的。作为一名 Java 的追随者，聊聊各种有趣或者有坑的 Java 技术。

Java Follower

3k 声望
317 粉丝
0 条评论