原博客链接:http://blog.csdn.net/aozil_yang/article/details/53538854
大体题意:
给你a和b,让你求出X和Y,使得X + Y = a lcm(x,y) = b
思路:
看数据范围肯定不能进行暴力枚举了!
令gcd(x,y) = g;
那么
g * k1 = x;
g * k2 = y;
因为g 是最大公约数,那么k1与k2 必互质!
=> g*k1*k2 = b
=> g*k1 + g * k2 = a;
所以k1 * k2 = b / g;
k1 + k2 = a/g;
因为k1与k2 互质!
所以k1 * k2 和 k1 + k2 也一定互质(一个新学的知识点= = )
所以a/g 与b/g也互质!
那么g 就是gcd(a,b);
所以我们得出一个结论: gcd(x,y) == gcd(a,b);;
所以x + y 与 x * y都是已知的了,解一元二次方程即可!
数学表达思路:
x+y=a;
lcm(x,y)=b=(x*y)/gcd(x,y);
gcd(x,y)=gcd(a,b);
x*y=b*gcd(a,b);<==(x+y=a,x*y=b)
(a-y)*y=b*gcd(a,b);
Y*y-a*y+b*gcd(a,b)=0;
==>y=(a+sqrt(a*a-、+4*b*gcd(a,b)))/2;
不符合情况的条件:一元二次方程无解、根号下结果不为整数、y不为整数 。
#include<cstdio>
#include<cstring>
#include<cmath>
using namespace std;
int gcd(int x,int y)
{
int temp;
while(y!=0)
{
temp=x%y;
x=y;
y=temp;
}
return x;
}
int main()
{
int a,b;
while(scanf("%d %d",&a,&b)!=EOF)
{
int m=gcd(a,b);
int B=b*m;
int tp=a*a-4*B;
int p=sqrt(tp);
int z=a+p;
if(p<0||p*p!=tp||z%2!=0)
printf("No Solution\n");
else
{
int x=(a+p)/2;
int y=a-x;
printf("%d %d\n",x<y?x:y,x>y?x:y);//结果从小到大输出
}
}
return 0;
}
A Simple Math Problem
Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 65536/65536 K (Java/Others)Total Submission(s): 602 Accepted Submission(s): 233
Given two positive integers a and b,find suitable X and Y to meet the conditions: X+Y=a Least Common Multiple (X, Y) =b
6 8 798 10780
No Solution 308 490