题意:给出a和b的gcd和lcm,让你求a和b。按升序输出a和b。若有多组满足条件的a和b,那么输出a+b最小的。
思路:lcm=a*b/gcd
     lcm/gcd=a/gcd*b/gcd
可知a/gcd与b/gcd互质,由此我们可以先用Pollard_rho法对lcm/gcd进行整数分解,
然后对其因子进行深搜找出符合条件的两个互质的因数,然后再都乘以gcd即为输出答案。

#include <iostream>
#include <stdio.h>
#include <algorithm>
#include <string.h>
#include <cstdlib>
#include <cmath> using namespace std;
const int maxn=;
long long lcm,gcd,n;
long long factor[maxn],fac[maxn];
long long Max;
long long aa,bb;
int cnt=,len=;
long long multi(long long a,long long b,long long mod){
long long ret=;
while(b){
if(b&){
ret=(ret+a)%mod;
}
a=a<<;
a=a%mod;
b=b>>;
}
return ret;
}
long long quickPow(long long a,long long b,long long mod){
long long ret=;
while(b){
if(b&)
ret=multi(ret,a,mod);
a=multi(a,a,mod);
b=b>>;
}
return ret;
}
bool witness(long long a,long long n){
long long m=n-;
int j=;
while(!(m&)){
j++;
m=m>>;
}
long long x=quickPow(a,m,n);
if(x==||x==n-)
return false;
while(j--){
x=multi(x,x,n);
if(x==n-)
return false;
}
return true;
}
//判定n是否为素数,若是,返回true
bool Miller_Rabin(long long n){
if(n==)
return true;
if(n< || !(n&))
return false;
for(int i=;i<;i++){
long long a=rand()%(n-)+;
if(witness(a,n))
return false;
}
return true;
}
long long Gcd(long long a,long long b){
return b==?a:Gcd(b,a%b);
} long long pollard_rho(long long n,int c){
long long x,y,d,i=,k=;
x=rand()%(n-)+;
y=x;
while(){
i++;
x=(multi(x,x,n)+c)%n;
d=Gcd((y-x+n)%n,n);
if(<d && d<n)
return d;
if(y==x)
return n;
if(i==k){
y=x;
k=k<<;
}
}
}
//对n进行质因数分解
void factorFind(long long n,int k){
if(n==)
return;
if(Miller_Rabin(n)){
factor[cnt++]=n;
return;
}
long long p=n;
while(p>=n)
p=pollard_rho(p,k--);
factorFind(p,k);
factorFind(n/p,k);
}
//dfs枚举a和b的值
void dfs(long long a,long long b,int k){
//如果目前a+b的值已经大于Max了,那么就直接return
if(a+b>=Max){
return;
}
if(k==len+){
if(a+b<Max){
Max=a+b;
aa=a;
bb=b;
}
return;
}
dfs(a*fac[k],b,k+);
dfs(a,b*fac[k],k+);
} int main()
{
long long a,b;
while(scanf("%I64d%I64d",&gcd,&lcm)!=EOF){
n=lcm/gcd;
//若n为素数的话,那aa=1,bb=lcm/gcd。
if(Miller_Rabin(n)){
//一开始WA的原因是,当gcd=1的时候,我是输出1,lcm
//后来才发现,比如1 40,输出5 8
aa=;
bb=n;
printf("%I64d %I64d\n",aa*gcd,bb*gcd);
}
else if(lcm==gcd){
printf("%I64d %I64d\n",gcd,gcd);
}
else{
cnt=;
factorFind(n,);
sort(factor,factor+cnt);
len=;
fac[]=factor[];
//这里由于对n分解质因数时,a/gcd 和 b/gcd肯定两两互质,所以先将相同的素因子先乘起来
//这样后面dfs时aa和bb肯定是两两互质的
for(int i=;i<cnt;i++){
if(factor[i]==factor[i-]){
fac[len]=fac[len]*factor[i];
}
else{
len++;
fac[len]=factor[i];
}
} //一开始RE,原因如下:
//当lcm=gcd时,n=lcm/gcd=1,那么a=fac[0]=0,n/a的时候会导致RE。。。
a=fac[];
b=;
Max=n/a+a;
aa=a;
bb=n/a;
dfs(a,b,);
if(aa>bb){
long long tmp=aa;
aa=bb;
bb=tmp;
}
printf("%I64d %I64d\n",aa*gcd,bb*gcd);
}
}
return ;
}

POJ 2429 GCD & LCM Inverse (Pollard rho整数分解+dfs枚举)的更多相关文章

  1. [POJ 2429] GCD & LCM Inverse

    GCD & LCM Inverse Time Limit: 2000MS   Memory Limit: 65536K Total Submissions: 10621   Accepted: ...

  2. POJ 2429 GCD & LCM Inverse(Pollard_Rho+dfs)

    [题目链接] http://poj.org/problem?id=2429 [题目大意] 给出最大公约数和最小公倍数,满足要求的x和y,且x+y最小 [题解] 我们发现,(x/gcd)*(y/gcd) ...

  3. POJ2429 GCD & LCM Inverse pollard_rho大整数分解

    Given two positive integers a and b, we can easily calculate the greatest common divisor (GCD) and t ...

  4. POJ 2429 GCD & LCM Inverse(Miller-Rabbin素性测试,Pollard rho质因子分解)

    x = lcm/gcd,假设答案为a,b,那么a*b = x且gcd(a,b) = 1,因为均值不等式所以当a越接近sqrt(x),a+b越小. x的范围是int64的,所以要用Pollard_rho ...

  5. POJ:2429-GCD & LCM Inverse(素数判断神题)(Millar-Rabin素性判断和Pollard-rho因子分解)

    原题链接:http://poj.org/problem?id=2429 GCD & LCM Inverse Time Limit: 2000MS Memory Limit: 65536K To ...

  6. poj 2429 GCD &amp; LCM Inverse 【java】+【数学】

    GCD & LCM Inverse Time Limit: 2000MS   Memory Limit: 65536K Total Submissions: 9928   Accepted:  ...

  7. POJ2429_GCD &amp; LCM Inverse【Miller Rabin素数測试】【Pollar Rho整数分解】

    GCD & LCM Inverse Time Limit: 2000MS Memory Limit: 65536K Total Submissions: 9756Accepted: 1819 ...

  8. POJ1811_Prime Test【Miller Rabin素数测试】【Pollar Rho整数分解】

    Prime Test Time Limit: 6000MS Memory Limit: 65536K Total Submissions: 29193 Accepted: 7392 Case Time ...

  9. POJ1811_Prime Test【Miller Rabin素数測试】【Pollar Rho整数分解】

    Prime Test Time Limit: 6000MS Memory Limit: 65536K Total Submissions: 29193 Accepted: 7392 Case Time ...

随机推荐

  1. 【bzoj2823】 AHOI2012—信号塔

    http://www.lydsy.com/JudgeOnline/problem.php?id=2823 (题目链接) 题意 求最小圆覆盖 Solution 关于最小圆覆盖的做法,论文里面都有.其实真 ...

  2. 超级懒汉编写的基于.NET的微信SDK

    一.前言 特别不喜欢麻烦的一个人,最近碰到了微信开发.下载下来了一些其他人写的微信开发“框架”,但是被恶心到了,实现的太臃肿啦. 最不喜欢的就是把微信返回的xml消息在组装成实体类,所以会比较臃肿,现 ...

  3. Maven学习笔记-03-Eclipse下maven项目在Tomcat7和Jetty6中部署调试

    现在最新的Eclipse Luna Release 已经内置了Maven插件,这让我们的工作简洁了不少,只要把项目直接导入就可以,不用考虑插件什么的问题,但是导入之后的项目既可以部署在Tomcat也可 ...

  4. UISearchBar和 UISearchDisplayController的使用

    感觉好多文章不是很全面,所以本文收集整合了网上的几篇文章,感觉有互相补充的效果. 如果想下载源码来看:http://code4app.com/search/searchbar .本源码与本文无关 1. ...

  5. Jmeter安装使用教程

    解压jakarta-jmeter-X.X.zip至至如c盘:C:/jakarta-jmeter-2.2目录下.      桌面上选择“我的电脑”(右键),高级, 环境变量, 在“系统变量”---> ...

  6. MSN

    msn (微软软件) 编辑 MSN,全称Microsoft Service Network,是微软公司(Microsoft)旗下的门户网站. MSN(门户网站)提供包括必应搜索.文娱.健康.理财.汽车 ...

  7. ExtJS学习之路第六步:深入讨论组件Panel用法

    Panel加载页面 var myPanel=Ext.create('Ext.panel.Panel',{ bodyPadding: "15px 10px 0 10px", titl ...

  8. C语言运算符优先级和口诀 (转)

    一共有十五个优先级: 1   ()  []  .  -> 2   !  ~   -(负号) ++  --   &(取变量地址)*   (type)(强制类型)    sizeof 3   ...

  9. Entity Framework 系统约定配置

    前言 Code First之所以能够让开发人员以一种更加高效.灵活的方式进行数据操作有一个重要的原因在于它的约定配置.现在软件开发越来越复杂,大家都试图将软件设计的越来越灵活,很多内容我们都希望是可配 ...

  10. ACM Computer Factory(dinic)

    ACM Computer Factory Time Limit: 1000MS   Memory Limit: 65536K Total Submissions: 5596   Accepted: 1 ...