題目
輸入整數N,計算1~N這N個數的最小公倍數,N<100
思路
思路其實很清晰,只要求得了前N-1個數的最小公倍數a,那么N個數的最小公倍數就是a和N的最小公倍數。求兩個整數\(a,b\) 的最小公倍數就是 \(\frac{a\times b}{gcd(a,b)}\),\(gcd(a,b)\)為a和b的最大公約數。看起來似乎很簡單,但是這里有個大坑:值越界。
題目中限制了N<100,但是當 N=23 的時候,計算得到的最小公倍數為5354228880已經遠遠超過了int型的表示范圍。
方法一
通過質因數求解。例如對於4和10,4的質因數為(2,2),10的質因數為(2,5)。由於他們有一個公共質因數2,所以最小公倍數為2*2*5=20。
所以第一步先求所有N個數的質因數,重復的質因數只能算一次,接下來將所有質因數相乘就可以得到最小公倍數。但其實這里還是有大數的問題,所以需要通過大數相乘的方法計算,也就是通過數組保存大數。代碼如下:
import java.util.Scanner;
public class Main{
public static void main(String[] arg){
Scanner sc = new Scanner(System.in);
int n = sc.nextInt();
int[] a = new int[105]; // a[1]~a[N]存儲 1~N 的N個數的所有質因數
int[] nums = new int[100]; // 將結果從低位到高位存在一個數組里
for(int i = 1; i <= 101; i++){
a[i] = i;
}
// 計算質因數存到a中
// 此時實質上a[1]*a[2]*...*a[N]就是1~N的最小公倍數
// 但直接相乘會數值溢出,因此用數組來進行大數相乘
for(int i = 2; i <= 101; i++){
for(int j = i + 1; j <= 101; j++){
if(a[j] % a[i] == 0){
a[j] /= a[i];
}
}
}
nums[0] = 1;
// tag存放進位,count存放有效數組長度
int tag = 0, count = 0;
for(int i = 2; i <= n; i++){
if(a[i] > 1){ // 減少不必要的計算
for(int j = 0; j <= count || tag > 0; j++){
int tmp = nums[j] * a[i] + tag;
nums[j] = tmp % 10;
tag = tmp / 10;
if(j > count){ // 更新有效長度
count = j;
}
}
}
}
while(count >= 0){ // 最后將nums中的有效數字從高位到低位輸出
System.out.print(nums[count]);
count--;
}
System.out.println();
}
}
方法二
java.math包中提供了BigInteger類用來處理大整數的問題。這里用另一種思路:小於N的質數最大冪乘積的方式。
例如N=10,小於10的質數有:2,3,5,7
對應的最大冪分別為:3,2,1,1(即質數的最大冪次方小於N)
因此前1~10的最小公倍數為2^3 * 3^2 * 5 * 7 = 2520
代碼如下:
import java.math.BigInteger;
import java.util.Scanner;
public class Main{
public static void main(String[] arg){
Scanner sc = new Scanner(System.in);
int n = sc.nextInt();
BigInteger ans = BigInteger.ONE;
for(int i = 2; i <= n; i++){
int tmp = 1;
if(isPrime(i)){
while(tmp * i <= n){
tmp *= i;
}
}
ans = ans.multiply(BigInteger.valueOf(tmp));
}
System.out.println(ans);
}
private static boolean isPrime(int a){
for(int i = 2; i <= Math.sqrt(a); i++){
if(a % i == 0){
return false;
}
}
return true;
}
}
參考來源
https://blog.csdn.net/sharing_li/article/details/8737855?utm_medium=distribute.pc_relevant.none-task-blog-baidujs-1
https://www.xuebuyuan.com/2857576.html
