Java 线程池(fork/join) 阶乘

该博客展示了如何利用Java的ForkJoinPool和BigInteger类来实现大整数的阶乘计算。首先,通过Random类生成指定范围内的随机数,然后计算其阶乘。接着,通过递归任务JieC类,利用ForkJoinPool进行并行计算,提高了计算效率。此方法特别适合处理超过long类型表示范围的阶乘问题。
摘要由CSDN通过智能技术生成

 

目录

 说明:

 代码段:

1、生成一个随机数

 2、利用随机数求阶乘

 3、使用ForkJoinPool 利用BigInteger求阶乘

 总结


 说明:

 一个简单利用ForkJoinPool的分段阶乘

 代码段:

1、生成一个随机数

使用种子产生随机数。要求输入一个整数做为种子,产生 10000(含)~11000(含)之间的随机整数,对于相同的种子,产生的随机数序列是固定的。

import java.util.Random;
import java.util.Scanner;

public class Ram {
	private static Scanner scanner;

	public static void main(String[] args) {
		scanner = new Scanner(System.in);
		long seed = scanner.nextLong();
		Random r = new Random(seed);
		/*
		 * 设a<b, 要产生一个[a,b)之间的随机数的公式为: 
		 * int value = a+random.nextInt(b-a);
		 */
		int value = 10000 + r.nextInt(1001);
		System.out.println("种子产生的结果 "+value);

	}
}

 2、利用随机数求阶乘

 参考例1,输入种子,然后产生 5(含)~10(含)之间的随机数。求阶乘。

import java.math.BigInteger;
import java.util.Random;
import java.util.Scanner;

public class RamJC {
	private static Scanner scanner;

	public static void main(String[] args) {
		scanner = new Scanner(System.in);
		long seed = scanner.nextLong();
		Random r = new Random(seed);
		int value = 5 + r.nextInt(6);
		BigInteger b = BigInteger.valueOf(value);
		System.out.println(b + "");
		BigInteger b3 = JieC(b);
		System.out.println(b3 + "");
	}

	private static BigInteger JieC(BigInteger b) {
		int x = b.intValue();
		int num = 1;
		for (int i = 2; i <= x; i++) {
			num = num * i;
		}
		BigInteger b2 = BigInteger.valueOf(num);
		return b2;
	}
}

 3、使用ForkJoinPool 利用BigInteger求阶乘

 输入整数做为种子,随机产生一个5000~6000之间的整数(含5000和6000) ,计算阶乘

import java.math.BigInteger;
import java.util.ArrayList;
import java.util.List;
import java.util.Random;
import java.util.Scanner;
import java.util.concurrent.ExecutionException;
import java.util.concurrent.ForkJoinPool;
import java.util.concurrent.ForkJoinTask;
import java.util.concurrent.RecursiveTask;

public class Main {
	static public final int NUM = 100;
	private static Scanner scanner;

	public static void main(String[] args) throws InterruptedException, ExecutionException {
		scanner = new Scanner(System.in);
		long seed = scanner.nextLong();
		Random r = new Random(seed);
		int value = 5000 + r.nextInt(1001);
		System.out.println(value + "");

		JieC jiec = new JieC(1, value, value);
		// 线程数默认Runtime.getRuntime().availableProcessors()
		ForkJoinPool forkJoinPool = new ForkJoinPool();
		ForkJoinTask<BigInteger> future = forkJoinPool.submit(jiec);
		System.out.println("最终结果 " + future.get());
	}
}

class JieC extends RecursiveTask<BigInteger> {
	private int MAX;
	private int max;
	private int min;

	public JieC(int min, int max, int MAX) {
		this.min = min;
		this.max = max;
		this.MAX = MAX;
	}

	@Override
	protected BigInteger compute() {
		int threadHold = (int) Math.ceil(MAX * 1.0 / Main.NUM); // 每组所所拥有的数字个数
		BigInteger count = BigInteger.valueOf(1);
		if ((max - min) <= threadHold) { // 最后一组
			for (int i = min; i <= max; i++) { // 累乘
				BigInteger x = BigInteger.valueOf(i);
				count = count.multiply(x);
			}
			System.out.println("这里的count " + count);
		} else {
			List<JieC> listTasks = new ArrayList<JieC>();
			for (int i = 0; i < Math.ceil(max * 1.0 / threadHold); i++) { // 能分的组数
				int end = (i + 1) * threadHold;
				if (end >= max) {
					end = max;
				}
				int start = i * threadHold + 1;
				JieC jiec = new JieC(start, end, MAX);
				listTasks.add(jiec);
			}

			for (JieC jiec : listTasks) {
				jiec.fork();
			}
			for (JieC jiec : listTasks) {
				count = count.multiply(jiec.join());
			}

		}
		return count;
	}
}

 总结

例题三 用BigInteger,因为22的阶乘结果就超过long的表示范围了。

聪明的朋友可以试试输出这个阶乘的前100位。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值