zoukankan      html  css  js  c++  java
  • 【算法】RSA解密(素数筛+欧几里得扩展+快速幂+快速乘)

    今天做了2019届蓝桥杯省赛A组的RSA解密问题。

    初看就觉得头大,后来学了快速幂,感觉可以用逆元求e。

    已知n和d。

    首先我们根据n=pq,然后列举求得p,q。

    1 LL n = 1001733993063167141;
    2 LL p = 3;
    3 while (p <= sqrt(n)) {
    4     if (n%p == 0 && isPrime(p) && isPrime(n/p)) {
    5         cout << p <<"  "<< n / p<<endl;
    6     }
    7     p++;
    8 }

    等个不到一分钟时间,就可以得出

    LL p = 891234941, q = 1123984201;

    然后根据d*e=1 (Mod (p-1)*(q-1))得出d和e在模(p-1)*(q-1)下护卫乘法逆元。

    因为d已知,所以我们可以通过拓展欧几里得来解e。

    具体拓展欧几里得可以看这里https://www.cnblogs.com/Judge/p/9383034.html#_lab2_1_1

     1 LL exgcd(LL a, LL b, LL &x, LL &y)
     2 {
     3     if (b == 0)
     4     {
     5         x = 1, y = 0;
     6         return a;
     7     }
     8     LL r = exgcd(b, a%b, x, y);
     9     LL tmp = x; x = y; y = tmp - (a / b)*y;
    10     return r;
    11 }
    12 
    13 LL mod_reverse(LL a, LL n)//ax=1(mod n) 求a的逆元x d*e=1mod(m)
    14 {
    15     LL d, x, y;
    16     d = exgcd(a, n, x, y);
    17     if (d == 1)
    18         return (x%n + n) % n;
    19     else
    20         return -1;
    21 }
    22 int main() {
    23     LL n = 1001733993063167141;
    24     LL p = 891234941, q = 1123984201;
    25     LL inv = (p - 1)*(q - 1);
    26     LL d = 212353;
    27     LL e = mod_reverse(d, inv);//823816093931522017
    28     cout << e<<endl;
    29 }

    对了,LL是通过typedef long long LL;弄出来的。

    最后用快速幂和快速乘求X。

     1 LL mult_mod(LL a, LL b, LL p) {
     2     LL res = 0;
     3     while (b) {
     4         if (b & 1) res = (res + a) % p;
     5         a = (a + a) % p;
     6         b >>= 1;
     7     }
     8     return res;
     9 }
    10 
    11 LL pow_mod(LL a, LL b, LL p) {//a的b次方求余p
    12     LL ret = 1;
    13     while (b) {
    14         //由于直接乘会溢出,所以我们使用快速乘来防止爆范围
    15         if (b & 1) ret = mult_mod(ret, a, p);
    16         a = mult_mod(a, a, p);
    17         b >>= 1;
    18     }
    19     return ret;
    20 }
    cout << pow_mod(20190324, e, n);//579706994112328949

    O(∩_∩)O哈哈~搞定了。

  • 相关阅读:
    docker-linux下的部署和基本命令
    Docker——Docker安装Sentinel
    分布式事务
    Git仓库完整迁移
    JWT token过期自动续期解决方案
    ORACLE用户的创建与授只读权
    Arthas-Java的线上问题定位工具
    mysql读写分离
    redis集群搭建-3.0/4.0版本
    相信自己,只要你努力了,你的梦想就可以实现
  • 原文地址:https://www.cnblogs.com/zyyz1126/p/12371865.html
Copyright © 2011-2022 走看看