整理的算法模板合集: ACM模板

点我看算法全家桶系列!!!

实际上是一个全新的精炼模板整合计划


繁凡出品的全新系列:解题报告系列 —— 超高质量算法题单,配套我写的超高质量的题解和代码,题目难度不一定按照题号排序,我会在每道题后面加上题目难度指数(1∼51 \sim 51∼5),以模板题难度 111 为基准。


这样大家在学习算法的时候就可以执行这样的流程:

%
阅读【学习笔记】 / 【算法全家桶】学习算法 ⇒\Rightarrow⇒ 阅读相应算法的【解题报告】获得高质量题单 ⇒\Rightarrow⇒ 根据一句话题解的提示尝试自己解决问题 ⇒\Rightarrow⇒ 点开详细题解链接学习巩固(好耶)
%
要是26个英文字母用完了我就接上24个希腊字母,我就不信50道题不够我刷的hhh
%
解题报告系列合集:【解题报告系列】超高质量题单 + 题解(ICPC / CCPC / NOIP / NOI / CF / AT / NC / P / BZOJ)

本题单前置知识:《算法竞赛中的初等数论》(二)正文 0x20同余(ACM / OI / MO)(十五万字符数论书)

目录

  • A、(P3868 [TJOI2009])猜数字
  • B、(P2480 [SDOI2010])古代猪文
  • C、(P4774 [NOI2018]) 屠龙勇士
  • D、(Codeforces 707Div. 2) D - Two chandeliers
  • E、(2018 CCPC-Final K)Mr. Panda and Kakin
  • F、(2019 ICPC 徐州网络赛 A) Who is better?

A、(P3868 [TJOI2009])猜数字

Weblink

https://www.luogu.com.cn/problem/P3868

Problem

Solution

bi∣(n−a+i)n−ai%bi=0n−ai≡0(modbi)n≡ai(modbi)\begin{aligned} & b_i\ |\ (n - a+i) \\ &n - a_i\%b_i=0\\&n-a_i\equiv0(\mod b_i)\\&n\equiv a_i(\mod b_i)\end{aligned}​bi​ ∣ (n−a+i)n−ai​%bi​=0n−ai​≡0(modbi​)n≡ai​(modbi​)​

显然有 nnn 个同余方程,直接CRT解方程组即可。

注意数据保证 ∏i=0kbi≤1018\prod\limits_{i=0}^{k}b_i\le 10^{18}i=0∏k​bi​≤1018,即 M≤1018M\le 10^{18}M≤1018,那么CRT的过程中随便一乘就会爆 long long ,所以要用快速乘。用 lognlognlogn 的快速乘竟然 T 了…所以需要加一些经典优化或者用 O(1)O(1)O(1) 的快速乘,可以处理小于 1.7×103081.7\times 10^{308}1.7×10308 的数据

Code

#include <bits/stdc++.h>
#include <algorithm>
#include <cstring>
#include <cmath>
#include <map>
#include <queue>
using namespace std;
#define int long long
typedef long long ll;
typedef int itn;
typedef pair<int, int> PII;
typedef pair<double, int> PDI;
const int N = 50 + 7, mod = 1e18 + 7, INF = 0x3f3f3f3f;
const double PI = acos(-1.0), eps = 1e-8;int n, t, kcase;
int M, m[N], a[N], k;
/*
int mul(int a, int b, int mod)
{int res = 0;while(b) {if(b & 1) res = (res + a) % mod;a = (a + a) % mod;b >>= 1;}return res;
}*/int mul(int x, int y, int p)
{int z = (long double)x / p * y;ll res = (unsigned long long)x * y - (unsigned long long) z * p;return (res + p) % p;
}ll exgcd(int a, int b, int &x, int &y)
{if(b == 0) {x = 1, y = 0;return a;}ll d = exgcd(b, a % b, x, y);ll z = x;x = y;y = z - y * (a / b);return d;
}void solve()
{ll M = 1;scanf("%lld", &k);for(int i = 1; i <= k; ++ i) {scanf("%lld", &a[i]);}for(int i = 1; i <= k; ++ i) {scanf("%lld", &m[i]);M *= m[i];}for(int i = 1; i <= k; ++ i) a[i] = (a[i] % m[i] + m[i]) % m[i];ll res = 0;for(int i = 1; i <= k; ++ i) {ll Mi = M / m[i];ll ti, y;ll d = exgcd(Mi, m[i], ti, y);ti = (ti % m[i] + m[i]) % m[i];res += mul(mul(a[i], ti, M), Mi, M);}printf("%lld\n", (res % M + M) % M);
}signed main()
{solve();return 0;
}

B、(P2480 [SDOI2010])古代猪文

Weblink

https://www.luogu.com.cn/problem/P2480

Problem

Solution

void 函数写成 ll 了,没有返回值 RE 了…

经典数论全家桶

懒得写题解了…


上述题解来源…

Code
简单实现一下就行了

#include <bits/stdc++.h>
using namespace std;
typedef long long ll;
typedef int itn;
const ll N = 5e5 + 7, p = 999911659, phi = 999911658, INF = 0x3f3f3f3f;
const double PI = acos(-1.0), eps = 1e-8;ll val;
ll a[10];
ll M = 1;
ll fact[N];
ll infact[N];
ll n, g, t, cnt;
ll mo[10] = {0, 2, 3, 4679, 35617};ll qpow(ll a, ll b, ll mod)
{ll res = 1;while(b) {if(b & 1) res = res * a % mod;a = a * a % mod;b >>= 1;}return res;
}ll exgcd(ll a, ll b, ll &x, ll &y)
{if(b == 0) {x = 1, y = 0;return a;}ll d = exgcd(b, a % b, x, y);ll z = x;x = y, y = z - y * (a / b);return d;
}void init(ll p)
{fact[0] = infact[0] = 1;for(ll i = 1; i < p; ++ i) {fact[i] = fact[i - 1] * i % p;infact[i] = infact[i - 1] * qpow(i, p - 2, p) % p;}
}ll C(ll a, ll b, ll p)
{if(a < b) return 0;return fact[a] * infact[b] % p * infact[a - b] % p;
}ll lucas(ll a, ll b, ll p)
{if(b == 0) return 1;if(a < p && b < p) return C(a, b, p);return C(a % p, b % p, p) * lucas(a / p, b / p, p) % p;
}ll CRT()
{ll res = 0;for(ll i = 1; i <= 4; ++ i) {ll Mi = M / mo[i];ll ti, y;ll d = exgcd(Mi, mo[i], ti, y);ti = (ti % mo[i] + mo[i]) % mo[i];res = (res + a[i] * ti % M * Mi % M) % M;}return (res % M + M) % M;
}void solve()
{M = phi;scanf("%lld%lld", &n, &g);if(g % p == 0) {puts("0");return ;}for(ll k = 1; k <= 4; ++ k) {init(mo[k]);for(ll i = 1; i * i <= n; ++ i) {if(n % i == 0) {a[k] = (a[k] + lucas(n, i, mo[k])) % mo[k];if(i * i != n)a[k] = (a[k] + lucas(n, n / i, mo[k])) % mo[k];}}}printf("%lld\n", qpow(g, CRT(), p));
}int main()
{solve();return 0;
}

C、(P4774 [NOI2018]) 屠龙勇士

Weblink

https://www.luogu.com.cn/problem/P4774

Problem

Solution

可以直接用 multiset 代替平衡树,计算出每条龙所需要的剑,并且这把剑是一定能打败这条龙的,不然最后方程组无解,就会输出 -1,所以我们直接把打败龙的奖励放入 set 里,再选下一把剑。显然题目中的恢复机制我们可以得到一个同余方程:

Cix≡Ai(modPi)\begin{aligned}&C_ix\equiv A_i(\mod P_i)\end{aligned}​Ci​x≡Ai​(modPi​)​

题目数据不保证 m[i] 一定互质 ⇒\Rightarrow⇒ excrt

一般的同余方程为:

x≡Ai(modPi)\begin{aligned}&x\equiv A_i(\mod P_i)\end{aligned}​x≡Ai​(modPi​)​

可以直接用拓展中国剩余定理。

但是本题的式子长这个样子:

Cix≡Ai(modPi)\begin{aligned}&C_ix\equiv A_i(\mod P_i)\end{aligned}​Ci​x≡Ai​(modPi​)​

考虑转成标准式子

Cix≡Ai(modPi)显然有 Cix+Piy=Aiexgcd解得 x’ y’x=x′+kbd=x′+kPigcd⁡(Pi,Ci)(modPigcd⁡(Pi,Ci))⇒x≡x′(modPigcd⁡(Pi,Ci))\begin{aligned}&C_ix\equiv A_i(\mod P_i)\\&\text{显然有\ }C_ix+P_iy=A_i\\&\text{exgcd解得 x' y'}\\&x =x'+k\frac{b}{d}\\&\ \ =x'+k\frac{P_i}{\gcd(P_i,C_i)}\\& (\mod{\frac{P_i}{\gcd(P_i,C_i)}})\\&\Rightarrow x\equiv x'(\mod\frac{P_i}{\gcd(P_i,C_i)}) \end{aligned}​Ci​x≡Ai​(modPi​)显然有 Ci​x+Pi​y=Ai​exgcd解得 x’ y’x=x′+kdb​  =x′+kgcd(Pi​,Ci​)Pi​​(modgcd(Pi​,Ci​)Pi​​)⇒x≡x′(modgcd(Pi​,Ci​)Pi​​)​

拓展中国剩余定理求解即可。

注意特判 Ai>PiA_i>P_iAi​>Pi​ 的情况即可,此时 Pi=1P_i=1Pi​=1,答案显然就是 max{A[i]use[i]}max\{\cfrac{A[i]}{use[i]}\}max{use[i]A[i]​}

Code

#include <bits/stdc++.h>
using namespace std;
typedef long long ll;
#define int long long
typedef pair<int, int> PII;
const ll N = 5e6 + 7, INF = 0x3f3f3f3f;
const double PI = acos(-1.0), eps = 1e-8;int n, m, k;
int A[N], P[N], award[N], atk[N], one;
multiset <int> st;
int C[N], use[N];
int ai[N], bi[N];void init()
{one = true;st.clear();memset(use, 0, sizeof use);
}int mul(int x, int y, int p)
{int z = (long double)x / p * y;int res = (unsigned long long)x * y - (unsigned long long) z * p;return (res + p) % p;
}int exgcd(int a, int b, int &x, int &y)
{if(b == 0) {x = 1, y = 0;return a;}int d = exgcd(b, a % b, x, y);int z = x;x = y, y = z - (a / b) * y;return d;
}int excrt()
{int x, y, k;int M = bi[1], ans = ai[1];for(int i = 2; i <= n; ++ i) {int a = M, b = bi[i], c = (ai[i] - ans % b + b) % b;int d = exgcd(a, b, x, y);int bg = b / d;if(c % d != 0) return -1;x = mul(x, c / d, bg);ans += x * M;M *= bg;ans = (ans % M + M) % M;}return (ans % M + M) % M;
}void sp_work()
{int ans = - INF;for(int i = 1; i <= n; ++ i) {if(use[i]) {ans = max(ans, (int)ceil((double)A[i] / use[i]));}}printf("%lld\n", ans);
}bool work()
{int x, y;for(int i = 1; i <= n; ++ i) {int a = use[i], b = P[i], c = A[i];int d = exgcd(a, b, x, y), bg = b / d;if(c % d != 0)return false;x = mul(x, c / d, bg);x = (x % b + b) % b;ai[i] = x;bi[i] = bg;}return true;
}void solve()
{init();scanf("%lld%lld", &n, &m);for(int i = 1; i <= n; ++ i) scanf("%lld", &A[i]);for(int i = 1; i <= n; ++ i) {scanf("%lld", &P[i]);if(A[i] > P[i])one = false;}for(int i = 1; i <= n; ++ i) scanf("%lld", &award[i]);for(int i = 1; i <= m; ++ i) {scanf("%lld", &atk[i]);st.insert(atk[i]);}for(int i = 1; i <= n; ++ i) {multiset <int> :: iterator it;if(A[i] < *st.begin()) it = st.begin();else it =  -- st.upper_bound(A[i]);use[i] = *it;st.insert(award[i]);st.erase(it);}if(one == false) {sp_work();return ;}bool win = work();if(win == 0) {puts("-1");return ;}printf("%lld\n", excrt());return ;
}signed main()
{int t;scanf("%lld", &t);while(t -- ) {solve();}return 0;
}/*
487472861809
3871865111
7560798679
584853762636
670310334583
*/

D、(Codeforces 707Div. 2) D - Two chandeliers

Weblink

https://codeforces.com/contest/1501/problem/D

Solution 1 二分 + 中国剩余定理

Solution 2 二分 + 拓展欧几里德

E、(2018 CCPC-Final K)Mr. Panda and Kakin

Weblink

https://codeforc.es/gym/102055/problem/K

Problem

Translation

给出 n,cn , cn,c , n=p∗qn = p ∗ qn=p∗q , ppp 和 qqq 是 xxx 附近相邻的两个质数, c=f230+3modnc = f^{2^{30}+3} \ mod\ nc=f230+3 mod n。求出 fff 的值。

Solution 1 中国剩余定理

Solution 2 拓展欧几里德

F、(2019 ICPC 徐州网络赛 A) Who is better?

Weblink

https://nanti.jisuanke.com/t/41383

Problem

Solution

斐波那契博弈 + 拓展中国剩余定理

…就是个板子题,只不过凉心数据会爆 long long…题目里也不给数据范围就离谱,n≤1015n\le 10^{15}n≤1015

#include <bits/stdc++.h>using namespace std;const int N = 5000007;
#define ll long long
#define LL __int128 LL n;
ll ai[N], bi[N];
LL f[N];LL exgcd(LL a, LL b, LL &x, LL &y)
{if(b == 0) {x = 1, y = 0;return a;}LL d = exgcd(b, a % b, x, y);LL z = x;x = y; y = z - a / b * y;return d;
}LL mul(LL a, LL b, LL c)
{LL res = 0;while(b) {if(b & 1) res = (res + a) % c;a = (a + a) % c;b >>= 1;}return res;
}LL EXCRT(int n)
{LL x, y, k;LL M = bi[1];LL ans = ai[1];for(int i = 2; i <= n; ++ i) {LL a = M, b = bi[i], c = (ai[i] - ans % b + b) % b;LL d = exgcd(a, b, x, y);LL bg = b / d;if(c % d != 0) return -1;x = mul(x, c / d, bg);ans += x * M;M *= bg;ans = (ans % M + M) % M;}return (ans % M + M) % M;
}//n = b (mod a)
//b -> ai(常数), a -> bi(模数)
ll k;int main()
{scanf("%lld", &k);for(ll i = 1; i <= k; ++ i) {scanf("%lld%lld", &bi[i], &ai[i]);}n = EXCRT(k);if(n == -1) {puts("Tankernb!");return 0;} f[1] = f[2] = 1;for(int i = 3; i <= 75; ++ i) {f[i] = f[i - 1] + f[i - 2];} for(int i = 1; i <= 75; ++ i) {if(f[i] == n) {puts("Lbnb!");return 0;}}puts("Zgxnb!");return 0;
}

解题报告(十三)中国剩余定理(ACM / OI)相关推荐

  1. 解题报告 (十三) 尺取法

    文章目录 尺取法 解题报告 PKU 2100 Graveyard Design PKU 3061 Subsequence PKU 2739 Sum of Consecutive Prime Numbe ...

  2. 【解题报告系列】超高质量题单 + 题解(ACM / OI)超高质量题解

    整理的算法模板合集: ACM模板 点我看算法全家桶系列!!! 实际上是一个全新的精炼模板整合计划 繁凡出品的全新系列:解题报告系列 -- 超高质量算法题单,配套我新写的超高质量的题解和代码,题目难度不 ...

  3. 解题报告(五)组合计数(ACM / OI)超高质量题解

    繁凡出品的全新系列:解题报告系列 -- 超高质量算法题单,配套我写的超高质量题解和代码,题目难度不一定按照题号排序,我会在每道题后面加上题目难度指数(1∼51 \sim 51∼5),以模板题难度 11 ...

  4. 解题报告(三)多项式求值与插值(拉格朗日插值)(ACM / OI)

    整理的算法模板合集: ACM模板 点我看算法全家桶系列!!! 实际上是一个全新的精炼模板整合计划 繁凡出品的全新系列:解题报告系列 -- 超高质量算法题单,配套我写的超高质量的题解和代码,题目难度不一 ...

  5. 解题报告(四)生成函数(ACM/ OI)

    整理的算法模板合集: ACM模板 点我看算法全家桶系列!!! 实际上是一个全新的精炼模板整合计划 繁凡出品的全新系列:解题报告系列 -- 超高质量算法题单,配套我写的超高质量的题解和代码,题目难度不一 ...

  6. 解题报告(二)多项式问题(多项式乘法及其各种运算)(ACM/ OI)超高质量题解

    整理的算法模板合集: ACM模板 点我看算法全家桶系列!!! 实际上是一个全新的精炼模板整合计划 繁凡出品的全新系列:解题报告系列 -- 超高质量算法题单,配套我写的超高质量的题解和代码,题目难度不一 ...

  7. 解题报告(一)快速沃尔什变换FWT(ACM / OI)超高质量题解

    整理的算法模板合集: ACM模板 点我看算法全家桶系列!!! 实际上是一个全新的精炼模板整合计划 繁凡出品的全新系列:解题报告系列 -- 超高质量算法题单,配套我写的超高质量的题解和代码,题目难度不一 ...

  8. 解题报告(八) prufer 序列与 Cayley 公式(ACM / OI)超高质量题解

    繁凡出品的全新系列:解题报告系列 -- 超高质量算法题单,配套我写的超高质量题解和代码,题目难度不一定按照题号排序,我会在每道题后面加上题目难度指数(1∼51 \sim 51∼5),以模板题难度 11 ...

  9. 解题报告(一)F、(2018 ACM - ICPC shenyang I)Distance Between Sweethearts(数学期望 + 乘法原理 + FWT)(4.5)

    繁凡出品的全新系列:解题报告系列 -- 超高质量算法题单,配套我写的超高质量题解和代码,题目难度不一定按照题号排序,我会在每道题后面加上题目难度指数(1∼51 \sim 51∼5),以模板题难度 11 ...

最新文章

  1. 分享codeigniter框架,在zend studio 环境下的代码提示
  2. 设置progressbar进度条颜色
  3. docker学习笔记(六)docker-compose
  4. mac定时执行python_Python脚本实现在Mac上DIY定时提醒功能
  5. mysql死锁查询_Mysql 查看死锁,解除死锁 方式
  6. java解析ajax的数据_java ajax 请求后获取 json 数据 以及 使用 解析 ,解惑
  7. TIOBE 11 月榜单:C、Swift、Go、D 与 Rust 起起伏伏
  8. camera android 黑屏,Android Camera.startPreview()启动未报错,但SurfaceView无画面输出
  9. 在线打mysql代码_mysql 在线alter table要留神_mysql
  10. 数据绑定之DataFormatString
  11. 配置paraview 服务器
  12. STM32对于1997与2007电表数据规约的解析
  13. 微信小程序消息订阅超详细流程步骤
  14. 计算机转魔方最快多少,最快的转魔方的算法?
  15. R740 U盘启动设置和安装centos7报错处理
  16. Oracle数据库的基础
  17. [bzoj4455][容斥原理][DP]小星星
  18. 营销型网站运营推广方法有哪些?最全的网站推广方式盘点!
  19. 代码随想录训练营day39
  20. Math类的常用方法,进一法,退一法,四舍五入法,绝对值,随机数 ,平方根 xy的次方

热门文章

  1. ​别再用方括号在Python中获取字典的值,试试这个方法
  2. 猫哥教你写爬虫 046--协程-实践-吃什么不会胖
  3. Mybatis之通用Mapper使用
  4. [React Router v4] Intercept Route Changes
  5. 借助阿里云数加,小小的美甲行业被美甲帮玩出了天价。
  6. git: No refs in common and none specified; doing no
  7. 学习使用资源文件[9] - WAVE 资源
  8. 嵌入式Linux综合知识
  9. nginx+tomcat实现集群负载均衡(实现session复制)
  10. VS2005中删除最近打开的项目和文件的记录