HDU3864 D_num
本文版权归ljh2000和博客园共有,欢迎转载,但须保留此声明,并给出原文链接,谢谢合作。
本文作者:ljh2000
作者博客:http://www.cnblogs.com/ljh2000-jump/
转载请注明出处,侵权必究,保留最终解释权!
题目链接:HDU3864
正解:Pollard−rho
解题报告:
Pollard−rho算法模板题。
考虑对于一个数n,我们有一个n以内的数对(x,y),若gcd(x−y,n)!=1,那么显然找到了一个n的因数g,递归往下做下去,分别分解质因子即可。
这个做法的期望次数会很少,可以想想生日悖论。
具体做法就是构造一个序列xi,xi=x2i−1+c,x0、c均为n以内不为0的随机数,我们就这样做下去,y就取2的次幂,x单增,直到找到为止。
发现有可能如果x0、c不好的话可能无解(出现环),需要多随几次,环的判断就是x、y某次突然相等了。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 | //It is made by ljh2000 //有志者,事竟成,破釜沉舟,百二秦关终属楚;苦心人,天不负,卧薪尝胆,三千越甲可吞吴。 #include <iostream> #include <cstdlib> #include <cstring> #include <cstdio> #include <cmath> #include <algorithm> #include <ctime> #include <vector> #include <queue> #include <map> #include <set> #include <string> #include <complex> #include <bitset> using namespace std; typedef long long LL; typedef long double LB; typedef complex< double > C; const double pi = acos (-1); LL n; vector<LL>w; inline int getint(){ int w=0,q=0; char c= getchar (); while ((c< '0' ||c> '9' ) && c!= '-' ) c= getchar (); if (c== '-' ) q=1,c= getchar (); while (c>= '0' &&c<= '9' ) w=w*10+c- '0' ,c= getchar (); return q?-w:w; } inline LL gcd(LL x,LL y){ if (y==0) return x; return gcd(y,x%y); } inline LL mul(LL x,LL y,LL mod){ LL r=0; while (y>0) { if (y&1) r+=x,r%=mod; x+=x; x%=mod; y>>=1; } return r; } inline LL fast_pow(LL x,LL y,LL mod){ LL r=1; while (y>0) { if (y&1) r=mul(r,x,mod); x=mul(x,x,mod); y>>=1; } return r; } inline int MillerRabin(LL n){ if (n==1) return 0; if (n==2) return 1; if (!(n&1)) return 0; LL aa=n-1,k=0,bb,lin,cc; while (!(aa&1)) aa>>=1,k++; int T=5; while (T--) { bb= rand ()%(n-1)+1; cc=fast_pow(bb,aa,n); for (LL i=1;i<=k;i++) { lin=mul(cc,cc,n); if (lin==1 && cc!=1 && cc!=n-1) return 0; cc=lin; } if (cc!=1) return 0; } return 1; } inline LL nex(LL x,LL c,LL n){ return (mul(x,x,n)+c)%n; } inline void pollardrho(LL n){ while (!(n&1)) n>>=1,w.push_back(2); if (n==1) return ; if (MillerRabin(n)) { w.push_back(n); return ; } LL x= rand ()%(n-1)+1,y=x,c= rand ()%(n-1)+1,g; for (LL i=1,j=1;;i++) { x=nex(x,c,n); g=gcd( abs (x-y),n); if (x==y) x= rand ()%(n-1)+1,y=x,c= rand ()%(n-1)+1,i=0,j=1; if (g>1 && g<n) break ; if (i==j) j<<=1,y=x; } pollardrho(g); pollardrho(n/g); } inline void work(){ srand ( time (NULL)); while ( scanf ( "%lld" ,&n)!=EOF) { if (n==1){ cout<< "is not a D_num" <<endl; continue ; } w.clear(); pollardrho(n); int t=w.size(); if (t!=2&&t!=3){ cout<< "is not a D_num" <<endl; continue ; } sort(w.begin(),w.end()); if (t==2) { if (w[0]!=w[1]) cout<<w[0]<< " " <<w[1]<< " " <<n<<endl; else cout<< "is not a D_num" <<endl; } else { if (w[0]==w[1] && w[1]==w[2]) cout<<w[0]<< " " <<w[0]*w[0]<< " " <<n<<endl; else cout<< "is not a D_num" <<endl; } } } int main() { work(); return 0; } //有志者,事竟成,破釜沉舟,百二秦关终属楚;苦心人,天不负,卧薪尝胆,三千越甲可吞吴。 |
本文作者:ljh2000
作者博客:http://www.cnblogs.com/ljh2000-jump/
转载请注明出处,侵权必究,保留最终解释权!
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】凌霞软件回馈社区,博客园 & 1Panel & Halo 联合会员上线
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】博客园社区专享云产品让利特惠,阿里云新客6.5折上折
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 开发中对象命名的一点思考
· .NET Core内存结构体系(Windows环境)底层原理浅谈
· C# 深度学习:对抗生成网络(GAN)训练头像生成模型
· .NET 适配 HarmonyOS 进展
· .NET 进程 stackoverflow异常后,还可以接收 TCP 连接请求吗?
· 本地部署 DeepSeek:小白也能轻松搞定!
· 基于DeepSeek R1 满血版大模型的个人知识库,回答都源自对你专属文件的深度学习。
· 在缓慢中沉淀,在挑战中重生!2024个人总结!
· 大人,时代变了! 赶快把自有业务的本地AI“模型”训练起来!
· Tinyfox 简易教程-1:Hello World!