package char3;
/**************************
* 解决相亲数问题
*************************/
public class AmicableNumbers {
private static int[][] amicableNumbers = new int[10000][2]; //存储相亲数的二维数组
private static int amicableNumbersCount = 0; //统计相亲数数目
public static void main(String[] args) {
long startTime = System.currentTimeMillis();
GetAmicableNumbers();
PrintAmicableNumbers();
long endTime = System.currentTimeMillis();
System.out.println("程序经历时间:"+(endTime - startTime) + "ms");
}
/****************************
*函数功能:获取相亲数
*函数参数:整形参数elem
*函数返回值:elem真因数之和
****************************/
private static void GetAmicableNumbers(){
for(int num = 3; num <= 100000; ++num){
int sumProperFactor = 0; //---真因数之和---//
sumProperFactor = GetProperFactor(num);
if(sumProperFactor > num && num == GetProperFactor(sumProperFactor)){ //---避免相等重复---//
amicableNumbers[amicableNumbersCount][0] = num;
amicableNumbers[amicableNumbersCount][1] = sumProperFactor;
amicableNumbersCount++;
}
}
}
/****************************
*函数功能:获取参数elem的真因数之和
*函数参数:整形参数elem
*函数返回值:elem真因数之和
****************************/
private static int GetProperFactor(int elem){
int total = 1;
/*一开始我采用的是i<= elem / 2 , 运行时间基本上在53000ms,将近一分钟,线性复杂度;但是我采用了这种限制方法之后,复杂度为Q(n二分之一次方,100000条数据基本上在400ms之内)*/
for(int i = 2; i <= (int)Math.sqrt(elem); ++i){
if(elem % i == 0){
total += i + elem / i;
}
}
return total;
}
/****************************
*函数功能:打印相亲数
****************************/
private static void PrintAmicableNumbers(){
for(int i = 0; i < amicableNumbersCount; i++)
{
System.out.println("第"+i+"组相亲数");
System.out.printf("%5d和%5d是一对相亲数", amicableNumbers[i][0],amicableNumbers[i][1]);
System.out.println("\n-------------------------------------\n");
}
}
}