URAL 1141. RSA Attack(欧拉定理+扩展欧几里得+快速幂模)

题目链接

题意 : 给你n,e,c,并且知道me ≡ c (mod n),而且n = p*q,pq都为素数。

思路 : 这道题的确与题目名字很相符,是个RSA算法,目前地球上最重要的加密算法。RSA算法原理 。

看到这个算法之后,就知道这个题是求cd≡m(mod n),要求m,就要先求d,而d则是e的模反元素。

如果两个正整数a和n互质,那么一定可以找到整数b,使得 ab-1 被n整除,或者说ab被n除的余数是1。这时,b就叫做a的模反元素。

由模反元素可知,ed≡1(mod Phi[n])(phi[n]代表n的欧拉函数)。

根据欧拉函数性质可知,phi[n] = (p-1)*(q-1)。

求e的逆元d需要用扩展欧几里得,ed+k*phi[n]=1.要注意处理求出的d是负数的情况。

最后求cd就要用到快速幂模,然后再MOD n 就是所求m。

#include <stdio.h>
#include <string.h>
#include <iostream>
typedef long long  LL ;

using namespace std ;

bool isprime(int n)
{
    for(int i = 2 ; i * i <= n ; i++)
    {
        if(n % i == 0) return false ;
    }
    return true ;
}
int multimod(int a,int n,int m)
{
    int tmp = a , res = 1 ;

    while(n)
    {
        //printf("11
") ;
        if(n & 1)
        {
            res *= tmp ;
            res %= m ;
        }
        tmp *= tmp ;
        tmp %= m ;
        n >>= 1 ;
        //printf("%d
",n) ;
    }
    return res ;
}
void exde(int a,int b,int &x,int& y)
{
    int t ;
    if(b == 0)
    {
        x = 1 ;
        y = 0 ;
        return ;
        //return a;
    }
     exde(b,a%b,x,y) ;
    t = x ;
    x = y ;
    y = t-(a/b)*y;
    //return d ;
}
int main()
{
    int T ,e,c,n;
    scanf("%d",&T) ;
    while(T--)
    {
        scanf("%d %d %d",&e,&n,&c) ;
        int p,q ,x,y;
        //printf("1
");
        for(int i = 2 ; i * i <= n ; i++)
        {
            if((n % i == 0) && isprime(i) && isprime(n / i))
            {
                p = i ;
                q = n / i ;
                break ;
            }
        }
        //printf("p = %d q = %d
",p,q) ;
        exde(e,(p-1)*(q-1),x,y);
        //printf("%d %d
",p,q) ;
        int d = x ;
        //printf("%d
",d+(p-1)*(q-1)) ;
        if(d < 0)
            d = (d+(p-1)*(q-1)) %((p-1)*(q-1)) ;
        //printf("%d
",d) ;
        int ans = multimod(c,d,n) ;
        printf("%d
",ans) ;
    }
    return 0 ;
}
View Code
原文地址:https://www.cnblogs.com/luyingfeng/p/4077184.html