import java.util.ArrayList;public class Main {public static void main(String args[]) {//常规思路/*long num = 2021041820210418l;int count = 0;for ( long i = 1 ; i < num ; i++ ){for ( long j = 1 ; j < num ; j++ ){for ( long k = 1 ; k < num ; k++ ){if ( i * j *um ){count++;}}}}*///显而易见,这个算法的时间复杂的非常的大。计算机想要算出结果,可能需要几天的时间//所以要另辟蹊径//想想,三个数相乘要等于num,那么这三个数是不是都是num的因子,都能被num整除呢?//上方的算法,三层for循环都是从1遍历到num,其中很多组合都是无效的//简而言之,这些无效组合中不能同时被num整除,而有效的组合,任何一个数都能被num整除//所以,如果我们能从num的因子里面去找组合,是不是时间复杂度就要小许多?long num = 2021041820210418l;//如果直接赋值,计算机默认数字是int类型,会报错。所以要在后面加'l',转换为long类型//定义一个ArrayList数组,存放num的因子ArrayList<Long> arr = new ArrayList<>();//从1开始遍历,遍历到num的平方根结束。不需要把num遍历一遍,这样算法复杂都也非常大,重点看for循环里面的语句for ( long i = 1 ; i <= Math.sqrt(num) ; i++ ){if ( num % i == 0 ){arr.add(i); //如果能被整除,就放到arr数组中//!!!重点在这里,当i能被num整除的情况下,求出num关于i的另外一个除数n//这样,for循环不需要从1遍历到num。可以通过较小的因子,求出另外一个较大的因子long n = num / i;//如果num = Math.sqrt(num)*Math.sqrt(num),那么由较小的因子求较大的因子时,会重复,要排除这种情况if ( n != i ){ //当然,此时num,不会出现这种情况。如果num=4,就会出现这种情况arr.add(n); //将较大的因子放入arr数组}}}//System.out.println(arr.size()); //num一共有128个因子//三层for循环依次遍历即可。 128^3 = 2097152 计算机完全可以在短时间内算出结果int count = 0;for ( long i : arr ){for ( long j : arr ){for ( long k : arr ){if ( i * j * k == num ){count++;}}}}System.out.println(count);}
}
不一定要每一个乘起来判断,也可以找到所有因数再一个一个遍历。这样可以减少时间复杂度。在数据大的时候可以这么算
import java.util.Scanner;
import java.util.ArrayList;
// 1:无需package
// 2: 类名必须Main, 不可修改//先求出该数的公因所有公因子,在循环遍历
//求出较小数后,使用除法;因此求到该数的平方根就行了
public class Main {public static void main(String[] args) {Scanner scan = new Scanner(System.in);long num=2021041820210418l;ArrayList<Long> arr=new ArrayList<>();for(long i=1;i<=Math.sqrt(num);i++){if(num%i==0){arr.add(i);long n=num/i;if(n!=i){arr.add(n);}}}long count=0;for(long i:arr){for(long j:arr){for(long k:arr){if(i*j*k==num){count++;}}}}System.out.print(count);scan.close();}
}