POJ 2115 模线性方程 ax=b(mod n)

/*
(x*c+a)%(2^k)==b →(x*c)%(2^k)==b-a
满足定理:
推论1:方程ax=b(mod n)对于未知量x有解,当且仅当gcd(a,n) | b。
    推论2:方程ax=b(mod n)或者对模n有d个不同的解,其中d=gcd(a,n),或者无解。

    定理1:设d=gcd(a,n),假定对整数x和y满足d=ax+by(比如用扩展Euclid算法求出的一组解)。
    如果d | b,则方程ax=b(mod n)有一个解x0满足x0=x*(b/d) mod n 。特别的设e=x0+n,
    方程ax=b(mod n)的最小整数解x1=e mod (n/d),最大整数解x2=x1+(d-1)*(n/d)。

    定理2:假设方程ax=b(mod n)有解,且x0是方程的任意一个解,则该方程对模n恰有d个不同的解(d=gcd(a,n)),
    分别为:xi=x0+i*(n/d) mod n 。
*/
#include<stdio.h>
__int64 ext_gcd(__int64  a,__int64 b,__int64 &x,__int64 &y)
{
    if(b==0){
        x=1;y=0; return a;
    }

        __int64 d=ext_gcd(b,a%b,x,y);
        __int64 t = x;
        x = y;
        y = t - a / b * y;
        return d;
}
__int64 modular_linear(__int64 a,__int64 b,__int64 n){
    __int64 d,e,x,y;
    d=ext_gcd(a,n,x,y);
    if(b%d)
        return -1;
    e=x*(b/d)%n+n;
    return e%(n/d);
}
int main(void)
{
     __int64 d,a,b,c,k;
    while(scanf("%lld %lld %lld %lld",&a,&b,&c,&k),a||b||c||k){
        d=modular_linear(c,b-a,(__int64)1<<k);
        if(d==-1)
            puts("FOREVER");
        else
            printf("%lld\n",d);
    }
    return 0;
}

POJ 2115 模线性方程 ax=b(mod n),布布扣,bubuko.com

时间: 2024-08-02 02:49:49

POJ 2115 模线性方程 ax=b(mod n)的相关文章

poj 2115 C Looooops (解模线性方程)

链接:poj 2115 题意:对于C语言的循环语句for(i=A ; i!=B ;i +=C), 问在k位存储系统中循环几次才会结束. 若在有限次内结束,则输出循环次数,否则输出死循环. 注:利用了 k位存储系统的数据特性进行循环(会溢出) 例如int型是16位的,那么int能保存2^16个数据, 即最大数为65535(本题默认为无符号), 当循环使得i超过65535时,则i会返回0重新开始计数 如i=65534,当i+=3时,i=1   即 i=(65534+3)%(2^16)=1 分析:设对

POJ2115——C Looooops(扩展欧几里德+求解模线性方程)

C Looooops DescriptionA Compiler Mystery: We are given a C-language style for loop of type for (variable = A; variable != B; variable += C) statement;I.e., a loop which starts by setting variable to value A and while variable is not equal to B, repea

POJ 2115 C Looooops(模线性方程)

http://poj.org/problem?id=2115 题意: 给你一个变量,变量初始值a,终止值b,每循环一遍加c,问一共循环几遍终止,结果mod2^k.如果无法终止则输出FOREVER. 思路: 根据题意原题可化成c * x = b - a mod (2 ^ k),然后解这个模线性方程. 1 #include<iostream> 2 #include<algorithm> 3 #include<cstring> 4 #include<cstdio>

poj 2115 (解单变元模线性方程)

http://poj.org/problem?id=2115 题意: 给出a,b,c,k,求x,使得(a+c*x)%(2^k)=b 限制: 0 <= a,b,c < 2^k; 1 <= k <= 32 思路: 拓展欧几里得单变元模线性方程 令 A=c;C=((b-a)%(2^k)+2^k)%(2^k);B=2^k 则这道题就化为Ax%n=B 对于Ax%B=C -> Ax+By=C -> d=Ext_gcd(A,B,x,y) //d其实为gcd(A,B) -> if

POJ 2115 (模线性方程 -&gt; 扩展欧几里得)

题意: for(i=A ; i!=B ;i +=C)循环语句,问在k位操作系统中循环结束次数. 若在有则输出循环次数. 否则输出死循环. 存在这样的情况:i= 65533 :i<=2:i+= 4:时i = 2: 由模线性方程->扩展欧几里得 #include <iostream> #include <cstdio> #include <cstdlib> #include <cstring> #include <queue> using

poj 2947 Widget Factory (高斯消元,解模线性方程)

链接:poj 2947 题意:生产一些零件,已知零件种数,记录条数 记录只记录了某次生产从周几开始,周几结束,以及生产了哪些产品. 每件商品生产所需天数为3-9天. 求每样产品需要多少天才能完成. 若无解输出Inconsistent data. 有无穷解输出Multiple solutions. 有唯一解,输出其解 分析:根据题目所给信息,可以列出同余方程组,再根据高斯消元求解, 但还得判断是无解,无穷解,还是唯一解 1.系数矩阵的秩若与增广矩阵的秩不相等,则无解,否则有解 2.若有解,若增广矩

[ACM] POJ 1061青蛙的约会(扩展欧几里得求模线性方程)

青蛙的约会 Time Limit: 1000MS   Memory Limit: 10000K Total Submissions: 89206   Accepted: 15926 Description 两只青蛙在网上相识了,它们聊得很开心,于是觉得很有必要见一面.它们很高兴地发现它们住在同一条纬度线上,于是它们约定各自朝西跳,直到碰面为止.可是它们出发之前忘记了一件很重要的事情,既没有问清楚对方的特征,也没有约定见面的具体位置.不过青蛙们都是很乐观的,它们觉得只要一直朝着某个方向跳下去,总能

POJ 2142 TheBalance 模线性方程求解

题目大意: 就是将两种砝码左右摆放,能够在物品放置在天平上时保持平衡 很容易得到 ax + by = t的模线性方程 按题目要求,希望首先满足 |x| + |y| 最小 , 如果有多种情况,再满足所有砝码质量最小,也就是a|x| + b|y|最小 x = x0 + b/g * k y = y0 - a/g * k 这里可以通过画一个2维坐标图进行观察 x , y 对于k的直线,我假定 b > a ,初始如果 a>b就交换两者数据,记得最后答案交换回来 因为a,b为砝码重量都大于0 所以x是递增

POJ 2115 C Looooops(扩展欧几里得应用)

题目地址:POJ 2115 水题..公式很好推.最直接的公式就是a+n*c==b+m*2^k.然后可以变形为模线性方程的样子,就是 n*c+m*2^k==b-a.即求n*c==(b-a)mod(2^k)的最小解.(真搞不懂为什么训练的时候好多人把青蛙的约会都给做出来了,这题却一直做不出来.....这两道不都是推公式然后变形吗.....) 代码如下: #include <iostream> #include <cstdio> #include <string> #incl