中国剩余定理CRT

中国剩余定理是要求我们解决这样的一类问题:

\[\begin{cases}x\equiv a_1\pmod {b_1} \\x\equiv a_2 \pmod{b_2}\\...\\x\equiv a_n\pmod{b_n} \end{cases}
\]

其中\(b_1,b_2,...,b_n\)互质。

我们先令\(m=\prod_{i=1}^{n}b_i,w_i=m/b_i\)

那么有\(gcd(m,w_i)==1\)

我们对于\(w_ix'+my'= 1\)解出来\(x',y'\)后

\(w_ix'a_i\equiv a_i\pmod {b_i}\)

所以现在就相当于解\(n=\sum_{i=1}^n w_ix'a_i\pmod m\)

一道例题 TJOI2009猜数字

题目链接:戳我

CRT的模板

有两点需要注意——一个是输入的数可能会有负数,二是乘法的时候可能会乘爆,需要用快速乘qwq

#include<iostream>
#include<cstdio>
#include<cstring>
#include<algorithm>
#include<cmath>
#define ll long long
#define MAXN 1010
using namespace std;
int n;
long long a[MAXN],b[MAXN];
inline ll fmul(ll x,ll y,ll mod)
{
ll cur_ans=0;
while(y>0)
{
if(y&1)cur_ans=(cur_ans+x)%mod;
x=(x+x)%mod;
y>>=1;
}
return cur_ans;
}
inline void exgcd(ll a,ll b,ll &x,ll &y)
{
if(b==0){y=0,x=1;return;}
exgcd(b,a%b,x,y);
int cur=x;
x=y;
y=cur-a/b*y;
}
inline ll china()
{
long long M=1,cur_ans=0,x,y;
for(int i=1;i<=n;i++) M*=b[i];
for(int i=1;i<=n;i++)
{
long long w=M/b[i];
exgcd(w,b[i],x,y);
x=(x%b[i]+b[i])%b[i];
cur_ans=(cur_ans+fmul(fmul(w,x,M),a[i],M))%M;
}
return (cur_ans+M)%M;
}
int main()
{
#ifndef ONLINE_JUDGE
freopen("ce.in","r",stdin);
#endif
scanf("%d",&n);
for(int i=1;i<=n;i++) scanf("%lld",&a[i]);
for(int i=1;i<=n;i++) scanf("%lld",&b[i]);
for(int i=1;i<=n;i++) a[i]=(a[i]%b[i]+b[i])%b[i];
printf("%lld\n",china());
return 0;
}

拓展中国剩余定理EXCRT

就是\(b_i\)不互质版本的......但是和中国剩余定理好像没有太大的关系qwq

我们假设已经解决了前k-1个方程,他们的解为ans,设\(m=\prod_{i=1}^{k-1}b_i\)。那么我们可以确定前k-1个方程的通解是\(ans+t*m\)。

现在的任务就是寻找一个t,使得\(ans+t*m\equiv a_i\pmod{b_i}\)

也就是\(t*m\equiv a_i-ans\pmod{b_i}\)

其实就是解\(a\equiv b\pmod {p}\)即\(ax+py=b\)的\(x',y'\)的解。

\(t=x'/gcd(m,b_i)*(a_i-ans)\)

\(ans=(ans+tm)\mod (\prod_{i=1}^{k-1}b_i)\)

一道模板

题目链接:戳我

#include<iostream>
#include<cstdio>
#include<cstring>
#include<algorithm>
#define MAXN 100010
#define ll long long
using namespace std;
int n;
long long a[MAXN],b[MAXN];
inline ll fmul(ll x,ll y,ll mod)
{
ll cur_ans=0;
while(y)
{
if(y&1) cur_ans=(cur_ans+x)%mod;
x=(x+x)%mod;
y>>=1;
}
return cur_ans;
}
inline ll exgcd(ll a,ll b,ll &x,ll &y)
{
if(b==0)
{
y=0,x=1;
return a;
}
ll ans=exgcd(b,a%b,x,y);
ll cur=x;
x=y;
y=cur-(a/b)*y;
return ans;
}
inline void solve()
{
ll ans=a[1],m=b[1],x,y;
for(int i=2;i<=n;i++)
{
ll B=((a[i]-ans)%b[i]+b[i])%b[i];
ll gcd=exgcd(m,b[i],x,y);
x=fmul(x,B/gcd,b[i]);
ans+=x*m;
m*=b[i]/gcd;
ans=(ans+m)%m;
}
printf("%lld\n",ans);
}
int main()
{
#ifndef ONLINE_JUDGE
freopen("ce.in","r",stdin);
#endif
scanf("%d",&n);
for(int i=1;i<=n;i++) scanf("%lld%lld",&b[i],&a[i]);
// for(int i=1;i<=n;i++) printf("%lld %lld\n",a[i],b[i]);
solve();
return 0;
}

CRT和EXCRT简单学习笔记的更多相关文章

  1. OI数学 简单学习笔记

    基本上只是整理了一下框架,具体的学习给出了个人认为比较好的博客的链接. PART1 数论部分 最大公约数 对于正整数x,y,最大的能同时整除它们的数称为最大公约数 常用的:\(lcm(x,y)=xy\ ...

  2. Log4j简单学习笔记

    log4j结构图: 结构图展现出了log4j的主结构.logger:表示记录器,即数据来源:appender:输出源,即输出方式(如:控制台.文件...)layout:输出布局 Logger机滤器:常 ...

  3. Linux——帮助命令简单学习笔记

    Linux帮助命令简单学习笔记: 一: 命令名称:man 命令英文原意:manual 命令所在路径:/usr/bin/man 执行权限:所有用户 语法:man [命令或配置文件] 功能描述:获得帮助信 ...

  4. 扩展中国剩余定理(EXCRT)学习笔记

    扩展中国剩余定理(EXCRT)学习笔记 用途 求解同余方程组 \(\begin{cases}x\equiv c_{1}\left( mod\ m_{1}\right) \\ x\equiv c_{2} ...

  5. <<C++标准程序库>>中的STL简单学习笔记

    0. 内容为个人学习笔记, 仅供参考, 如有错漏, 欢迎指正! 1. STL中的所有组件都是由模板构成的, 所以其元素可以是任意型别的. 组件有: - 容器: 管理某类对象的集合. 不同的容器有各自的 ...

  6. Mongoose简单学习笔记

    1.1 名词解释 Schema : 一种以文件形式存储的数据库模型骨架,不具备数据库的操作能力 Model : 由Schema发布生成的模型,具有抽象属性和行为的数据库操作对 Entity : 由Mo ...

  7. Linux——bash应用技巧简单学习笔记

    本人是看的lamp兄弟连的视频,学习的知识做一下简单,如有错误尽情拍砖. 命令补齐 命令补齐允许用户输入文件名起始的若干个字 母后,按<Tab>键补齐文件名. 命令历史 命令历史允许用户浏 ...

  8. Oracle简单学习笔记

    创建用户 CREATE USER username identified by password;//这是最简单的用户创建SQL语句. CREATE USER username identified ...

  9. Linux——软件包简单学习笔记

    Linux中的是那种软件包:  (这里学习是基于redHat的Cent-OS) 1: 二进制软件包管理(RPM.YUM) 2:源代码包安装 3: 脚本安装(Shell或Java脚本) 一: 二进制软件 ...

随机推荐

  1. popupMenu-----弹出菜单

    import android.os.Bundle; import android.app.Activity; import android.graphics.Color; import android ...

  2. 使用Linux之安装jdk 7

    工具/原料   jdk7源码安装压缩包 方法/步骤     卸载OpenJDK rpm -qa | grep java rpm -e --nodeps java-1.6.0-openjdk-1.6.0 ...

  3. IIS PHP Warning: Unknown: open(c:\\php\\tmp\\sess_xxx, O_RDWR) failed: Permission denied (13) in Unknown on line 0

    出现这个问题的原因是你修改了php保存session的路径,但没有给用户访问该目录的权限.   右键该目录,给users用户组读.写的权限.

  4. 3.说一下你了解的弹性FLEX布局.

    页面布局一直都是web应用样式设计的重点 我们传统的布局方式都是基于盒模型的 利用display.position.float来布局有一定局限性 比如说实现自适应垂直居中 随着响应式布局的流行,CSS ...

  5. 清除Pycharm设置的方法

    Mac 按需运行下面的 rm 删除命令 # Configuration rm -rf ~/Library/Preferences/PyCharm* # Caches rm -rf ~/Library/ ...

  6. 构建openssl debug版

    一.简介 作为一种安全协议,openssl囊括了主要的密码算法.常用的密钥和证书封装管理功能以及SSL协议,并提供了丰富的应用程序供测试或其它目的使用. 参考: http://www.linuxidc ...

  7. rpmdb open failed的解决办法

      错误信息如下:    “错误:无法从 /var/lib/rpm 打开软件包数据库      CRITICAL:yum.main:       Error: rpmdb open failed”   ...

  8. process概念

    multiprocess: multiprocess.cpu_count():统计cpu核数 multiprocess.active_chirdren():获取所有的子进程 multiprocess. ...

  9. UI设计:掌握这6点,轻松0到1

    非科班出身能成为UI设计师吗? 答案是肯定的.世上无难事,只怕有心人.只要找对方法.坚持不懈,即便是零基础也能学好UI设计. 那么零基础学习UI设计,需要学习哪些知识?我们要从哪些地方学起?怎么系统学 ...

  10. cocos sdkbox android 接入注意

    1 jin/Android.mk  中 LOCAL_SRC_FILES 链接的是runtime-src/Classes中的cpp文件 2  jin/Android.mk 若 LOCAL_LDLIBS ...