问题描述:
一天,鬼谷子随意从2-99中选取了两个数。他把这两个数的和告诉了庞涓,把这两个数
的乘积告诉了孙膑。但孙膑和庞涓彼此不知到对方得到的数。
第二天,庞涓很有自信的
对孙膑说:虽然我不知到这两个数是什麽,但我知道你一定也不知道。
随后,孙膑说:那我知道了。
庞涓说:那我也知道了。
解答:
1
庞娟:虽然我不知到这两个数是什麽,但我知道你一定也不知道。
从这句话中,可以得知,庞娟手里的数一定不能拆分为两个素数之和。
2
随后,孙膑说:那我知道了。
从这句话得知:
假如孙膑手里的数为num,
那num可以拆分为多对(num1,num2)使得num1 * num2 == num。
那其中肯定只有一对(num1,num2)使得num1+num2之和不能拆分为两个素数之和。这对(num1,num2)就是孙膑猜出来的数。
3
庞涓说:那我也知道了。
从这句话得知:
假如庞娟手里的数为num,
则num可以拆分为多对(num1,num2)使得num1 +num2 == num,
每对(num1,num2)可以形成一个num1 * num2的积num3,
每个 num3都可以拆分为多对(NUM1,NUM2),使得NUM1 * NUM2 == num3,
每个num3对应的多对(NUM1,NUM2),每对都能构造出NUM1 + NUM2 = NUM3,
肯定只存在一个num3所对应的所有NUM3都不能拆分为两个素数之和。
代码如下:
public class MyTest {
final int [] prime = {2,3,5,7,11,13,17,19,23,29
,31 ,37 ,41 ,43 ,47 ,53 ,59 ,61 ,67 ,71
,73 ,79, 83 ,89 ,97};//已知的100以内的素数
int primeSum[] = new int[1000],//用来存以上任两个素数的和
priLength; //primeSum数组的长度
void init(){ //计算出所有以上任两个素数的和,并存在primeSum数组中
for(int i=0;i<prime.length;i++){
for(int j=i;j<prime.length;j++){
primeSum[priLength++] = prime[i] + prime[j];
}
}
}
boolean isPrimeSum(int num){//判断sum这个数是否能用两个素数相加得到
for(int i = 0;i<priLength;i++){
if(primeSum[i] == num)
return true;
}
return false;
}
boolean isShuzi(int num){ //判断数字是否在[2,99]
if(num>=2 && num <=99)
return true;
return false;
}
/**
* 假如用两个数字的乘积构造出num的组合有n个。
* 判断n种组合中是否只有一个,两数之和不能用两个素数相加得到。
*/
boolean isOneProduct(int num){
int ProductSum = 0;
for(int i =2;i<=(int)Math.sqrt(num);i++){
if(num %i == 0 && isShuzi(i) && isShuzi(num/i)){
if(!isPrimeSum(i + num/i)){
ProductSum++;
}
}
}
if(ProductSum == 1)
return true;
return false;
}
/**
*
* 假如用两个数相加得到num的可能组合有n个。
* 那这n对数相乘得到的数中,判断是否只有一个数不能用两个素数相加得到。
*/
boolean isOneSum(int num){
int SumNum = 0;
for(int i =2;i<=num/2;i++){
if(isOneProduct(i*(num-i)))
SumNum++;
}
if(SumNum == 1)
return true;
return false;
}
public static void main(String[] args) {
MyTest a = new MyTest();
a.init();
for(int i =2;i<100;i++){
for(int j =i;j<100;j++){
if(!a.isPrimeSum(i+j) && a.isOneProduct(i*j) &&a.isOneSum(i+j) )
System.out.println("两个数为 "+i+" "+j);
}
}
}
}
答案为(4,13)。