P5170 【模板】类欧几里得算法(类欧)

P5170 【模板】类欧几里得算法

Description

要求在O(lgn)O(lgn)O(lgn)的时间内求出:
∑i=0n⌊ai+bc⌋\sum_{i = 0}^n{\lfloor\frac{ai+b}{c}\rfloor}i=0ncai+b

∑i=0ni⌊ai+bc⌋\sum_{i = 0}^n{i\lfloor\frac{ai+b}{c}\rfloor }i=0nicai+b

∑i=0n⌊ai+bc⌋2\sum_{i = 0}^n{\lfloor\frac{ai+b}{c}\rfloor^2}i=0ncai+b2

Solution

其实也就是一种优秀的求和思想。

Part one

我们先考虑最基本的第一个:
∑i=0n⌊ai+bc⌋=∑i=0n(⌊a′i+b′c⌋+pi+q)\sum_{i = 0}^n{\lfloor\frac{ai+b}{c}\rfloor} = \sum_{i = 0}^n{(\lfloor\frac{a'i+b'}{c}\rfloor} + pi + q)i=0ncai+b=i=0n(cai+b+pi+q)

其中p=⌊ac⌋,q=⌊bc⌋p =\lfloor\frac{a}{c}\rfloor, q = \lfloor\frac{b}{c}\rfloorp=ca,q=cb

那么后面的∑pi+q\sum{pi+q}pi+q很容易计算,因此问题转化为求:

f(a,b,c,n)=∑i=0n⌊ai+bc⌋(a∈[0,c),b∈[0,c))f(a,b,c,n)=\sum_{i = 0}^n{\lfloor\frac{ai+b}{c}\rfloor}(a\in[0,c),b\in[0, c))f(a,b,c,n)=i=0ncai+b(a[0,c),b[0,c))

Part two

然后使用一个极其诡妙的思路:
f(a,b,c,n)f(a,b,c,n)f(a,b,c,n)
=∑i=0n⌊ai+bc⌋= \sum_{i = 0}^n{\lfloor\frac{ai+b}{c}\rfloor}=i=0ncai+b
=∑i=0n∑j=1m[j≤⌊ai+bc⌋](m=⌊an+bc⌋)=\sum_{i = 0}^n\sum_{j = 1}^m{[j \leq \lfloor\frac{ai+b}{c}\rfloor}]\ \ (m = \lfloor\frac{an+b}{c}\rfloor)=i=0nj=1m[jcai+b]  (m=can+b)
=∑i=0n∑j=0m−1[jc+c≤ai+b]=\sum_{i = 0}^n\sum_{j = 0}^{m - 1}{[jc +c\leq ai+b]}=i=0nj=0m1[jc+cai+b]
=∑j=0m−1∑i=0n[jc+c≤ai+b]=\sum_{j = 0}^{m - 1}\sum_{i = 0}^n{[jc +c\leq ai+b]}=j=0m1i=0n[jc+cai+b]
=∑j=0m−1(n+1−∑i=0n[jc+c>ai+b])=\sum_{j = 0}^{m - 1}{(n + 1 - \sum_{i = 0}^n[jc +c> ai+b])}=j=0m1(n+1i=0n[jc+c>ai+b])
=∑j=0m−1(n−⌊jc+c−b−1a⌋)=\sum_{j = 0}^{m - 1}{(n -\lfloor\frac{jc+c-b-1}{a}\rfloor)}=j=0m1(najc+cb1)
=nm−∑j=0m−1⌊jc+c−b−1a⌋=nm-\sum_{j = 0}^{m - 1}\lfloor\frac{jc+c-b-1}{a}\rfloor=nmj=0m1ajc+cb1
=nm−f(c,c−b−1,a,m−1)=nm - f(c,c-b-1,a,m-1)=nmf(c,cb1,a,m1)

因此可以递归计算,直到a=0a=0a=0时,我们直接算出答案。

不难发现a,ca,ca,c相当于做了一个辗转相除的过程,因此时间复杂度为O(lgn)O(lgn)O(lgn)

Part three

剩下两个也是同样的思路,先考虑让a′=amodc,b′=bmodca'=a\mod c,b'=b\mod ca=amodc,b=bmodc,然后快速计算下取整式外的贡献,下取整式内的部分通过类似上面的方法转化,推导出若干个能用类欧计算的式子相加的形式,然后递归计算即可。这里不再赘述。

Code

#include <bits/stdc++.h>using namespace std;template<typename T> inline bool upmin(T &x, T y) { return y < x ? x = y, 1 : 0; }
template<typename T> inline bool upmax(T &x, T y) { return x < y ? x = y, 1 : 0; }#define MP(A,B) make_pair(A,B)
#define PB(A) push_back(A)
#define SIZE(A) ((int)A.size())
#define LEN(A) ((int)A.length())
#define FOR(i,a,b) for(int i=(a);i<(b);++i)
#define fi first
#define se secondtypedef long long ll;
typedef unsigned long long ull;
typedef long double lod;
typedef pair<int, int> PR;
typedef vector<int> VI; const lod eps = 1e-9;
const lod pi = acos(-1);
const int oo = 1 << 30;
const ll loo = 1ll << 60;
const int mods = 998244353;
const int inv2 = (mods + 1) >> 1;
const int inv6 = (mods + 1) / 6;
const int MAXN = 600005;
const int INF = 0x3f3f3f3f; //1061109567
/*--------------------------------------------------------------------*/namespace FastIO{constexpr int SIZE = (1 << 21) + 1;int num = 0, f;char ibuf[SIZE], obuf[SIZE], que[65], *iS, *iT, *oS = obuf, *oT = obuf + SIZE - 1, c;#define gc() (iS == iT ? (iT = ((iS = ibuf) + fread(ibuf, 1, SIZE, stdin)), (iS == iT ? EOF : *iS ++)) : *iS ++)inline void flush() {fwrite(obuf, 1, oS - obuf, stdout);oS = obuf;}inline void putc(char c) {*oS ++ = c;if (oS == oT) flush();}inline void getc(char &c) {for (c = gc(); !isalpha(c) && c != EOF; c = gc());}inline void reads(char *st) {char c;int n = 0;getc(st[++ n]);for (c = gc(); isalpha(c) ; c = gc()) st[++ n] = c;}template<class I>inline void read(I &x) {for (f = 1, c = gc(); c < '0' || c > '9' ; c = gc()) if (c == '-') f = -1;for (x = 0; c >= '0' && c <= '9' ; c = gc()) x = (x << 3) + (x << 1) + (c & 15);x *= f;}template<class I>inline void print(I x) {if (x < 0) putc('-'), x = -x;if (!x) putc('0');while (x) que[++ num] = x % 10 + 48, x /= 10;while (num) putc(que[num --]);}struct Flusher_{~Flusher_(){flush();}} io_Flusher_;
}
using FastIO :: read;
using FastIO :: putc;
using FastIO :: reads;
using FastIO :: print;struct Node{ int f, g, h; Node() { f = g = h = 0; }Node(int x, int y, int z):f(x), g(y), h(z){};
};
int S1(int x) { return 1ll * x * (x + 1) / 2 % mods; }
int S2(int x) { return 1ll * x * (x + 1) % mods * (x * 2 + 1) % mods * inv6 % mods; }
int upd(int x, int y) {return x + y >= mods ? x + y - mods : x + y; 
}
Node solve(int a, int b, int c, int n) {Node Ans, ans;int p = 0, q = 0;if (a >= c || b >= c) {p = a / c, q = b / c;Ans.f = upd(Ans.f, 1ll * p * S1(n) % mods);Ans.f = upd(Ans.f, 1ll * q * (n + 1) % mods);Ans.g = upd(Ans.g, 1ll * p * p % mods * S2(n) % mods);Ans.g = upd(Ans.g, 1ll * q * q % mods * (n + 1) % mods);Ans.g = upd(Ans.g, 2ll * p * q % mods * S1(n) % mods);Ans.h = upd(Ans.h, 1ll * p * S2(n) % mods);Ans.h = upd(Ans.h, 1ll * q * S1(n) % mods);a -= p * c, b -= q * c;}if (!a) return Ans;int m = ((ll)a * n + b) / c;Node t = solve(c, c - b - 1, a, m - 1);ans.f = upd(ans.f, upd(1ll * m * n % mods, mods - t.f));ans.h = upd(ans.h, upd(1ll * m * S1(n) % mods, mods - 1ll * upd(t.g, t.f) * inv2 % mods));ans.g = upd(ans.g, upd(2ll * ans.h * p % mods, 2ll * ans.f * q % mods));ans.g = upd(ans.g, 1ll * m * m % mods * n % mods);ans.g = upd(ans.g, mods - 2ll * t.h % mods);ans.g = upd(ans.g, mods - t.f);return Node(upd(ans.f, Ans.f), upd(ans.g, Ans.g), upd(ans.h, Ans.h));
}
signed main() {
#ifndef ONLINE_JUDGEfreopen("a.in", "r", stdin);
#endifint Case;read(Case);while (Case --) {int n, a, b, c;read(n), read(a), read(b), read(c);Node ans = solve(a, b, c, n);print(ans.f), putc(' '), print(ans.g), putc(' '), print(ans.h), putc('\n');}return 0;
}

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/315508.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

AtCoder Beginner Contest 192 F - Potion 背包dp

传送门 题意&#xff1a; 给你nnn个数&#xff0c;让后让你选出来kkk个AAA&#xff0c;把他们求和&#xff0c;之后再递增kkk直到正好达到xxx&#xff0c;求最小的递增次数。 思路&#xff1a; 转化一下题意就是求∑Ax(modlen)\sum Ax(\bmod\ \ len)∑Ax(mod len)&#xff0…

基于Dapper的开源Lambda扩展,且支持分库分表自动生成实体

LnskyDB是基于Dapper的Lambda扩展,支持按时间分库分表,也可以自定义分库分表方法开源地址 https://github.com/liningit/LnskyDB在此非常感谢SkyChenSky其中lambda表达式的解析参考了他的开源项目下面是用ProductSaleByDayEntity作为示例,其中StatisticalDate为分库分表字段,如…

P4887 【模板】莫队二次离线(第十四分块(前体))

P4887 【模板】莫队二次离线&#xff08;第十四分块(前体)&#xff09; Solution 简单学习了一下二次离线莫队&#xff0c;写了个板子题。 这题直接莫队时间复杂度为O(Cnn)O(Cn\sqrt n)O(Cnn​)&#xff0c;其中C(14k)C\binom{14}{k}C(k14​)&#xff0c;显然不太行。 我们…

P1297 [国家集训队]单选错位 期望

传送门 题意&#xff1a; 思路&#xff1a; 手推了一下没想到还真的能过。 对于相邻的两个数aia_iai​和ai1a_{i1}ai1​&#xff0c;分两种情况讨论&#xff1a; (1) ai<ai1a_i<a_{i1}ai​<ai1​ 时&#xff0c;答案在[1,ai][1,a_i][1,ai​]的范围内概率为aiai1\fra…

也读《人月神话》:没有银弹的软件工程

一、关于人月神话这本书记得在上大学的时候&#xff0c;就经常听学长和老师讲起《人月神话》&#xff0c;但是却一直没有阅读。记得当时一听到这个书名&#xff0c;还以为是个神马科幻类别的书&#xff0c;结果是个软件工程方面的书籍。这本书是“图灵奖得主、“IBM360系统之父…

CF1088F. Ehab and a weird weight formula(倍增)

CF1088F. Ehab and a weird weight formula Solution 这题大概是个大力找性质题&#xff08;莫名感觉学习文化课有利于找性质&#xff1f;&#xff01;&#xff1f;&#xff09;。 性质1&#xff1a;不难发现一个点比它权值小的有且仅有一个&#xff08;最小权点除外&#x…

P6154 游走 概率dp

传送门 题意&#xff1a; 思路&#xff1a; 给你个DAGDAGDAG&#xff0c;由于每一条路径出现概率相等&#xff0c;那么期望就是总长度路径个数\frac{总长度}{路径个数}路径个数总长度​。设f[i]f[i]f[i]表示到iii这个点的总长度&#xff0c;g[i]g[i]g[i]表示到iii这个点路径的…

[译]如何在C#中调试LINQ查询

LINQ是我在C#中最喜欢的功能之一。它让代码看起来更漂亮美观。我们得到了一个易于编写和理解的简洁函数式语法。好吧&#xff0c;至少我们可以使用LINQ方法的语法风格。LINQ很难进行调试。我们无法知道该查询内部发生了什么。我们可以看到输入和输出&#xff0c;但这就是它的全…

CF1303F - Number of Components(并查集)

CF1303F - Number of Components Solution 思路还是有点妙的。 容易想到并查集&#xff0c;但是并查集不容易维护删边&#xff0c;怎么办呢&#xff1f; 我们考虑拆贡献&#xff0c;把加边的贡献和删边的贡献拆开&#xff0c;分别维护。 只加边就是四连通加边&#xff0c;算…

CodeForces - 375D Tree and Queries 树启 + 思维

传送门 题意&#xff1a; 思路&#xff1a; 很明显子树问题会想到树启&#xff0c;让后如何updateupdateupdate呢&#xff1f;一个显然的思路就是维护一个树状数组&#xff0c;查询次数>kj>k_j>kj​的个数。但是这样复杂度是O(nlog2n)O(nlog^2n)O(nlog2n)的&#xf…

WebSocket数据加密——AES与RSA混合加密

前言之前在写“一套简单的web即时通讯”&#xff0c;写到第三版的时候没什么思路&#xff0c;正好微信公众号看到一篇讲API交互加密&#xff0c;于是就自己搞了一套AES与RSA混合加密&#xff0c;无意中产生应用在WebSocket想法&#xff0c;好在思路都差不多&#xff0c;稍微改动…

CF1365G Secure Password(构造,交互,二进制分组)

CF1365G Secure Password Solution 妙妙思维题。 注意到(136)>n\binom{13}{6}>n(613​)>n。&#xff08;谁tm能注意到这个&#xff1f;&#xff01;&#xff1f;&#xff09; 我们可以把所有13位二进制数中有6个1的拿出来给nnn个数重标号。然后对于每一位iii&…

基于 EntityFramework 生成 Repository 模式代码

借助 WeihanLi.EntityFramework 实现简单的 RepositoryIntro很多时候一些简单的业务都是简单的增删改查&#xff0c;动态生成一些代码完成基本的增删改查&#xff0c;而这些增删改查代码大多类似&#xff0c;只有一些有复杂业务逻辑的可能需要手动去写。于是实现了一个基于 EF …

Codeforces Round #601 (Div. 2)

传送门 文章目录A.Changing Volume题意&#xff1a;思路&#xff1a;B. Fridge Lockers题意&#xff1a;思路&#xff1a;C. League of Leesins题意&#xff1a;思路&#xff1a;D. Feeding Chicken题意&#xff1a;思路&#xff1a;E1 E2. Send Boxes to AliceA.Changing Volu…

CF1375G. Tree Modification(贪心,黑白染色)

CF1375G. Tree Modification Solution 假设我们取定了根&#xff0c;那么只可能从深度大的点接到深度小的点&#xff0c;我们每次取一个高度为2的子树接到该子树的父亲&#xff0c;这样取一定不劣&#xff0c;操作次数相当于是偶数深度点&#xff08;根深度为0&#xff09;的…

P3168 [CQOI2015]任务查询系统 主席树 + 差分

传送门 题意&#xff1a; 思路&#xff1a; 题目中(si,ei,pi)(s_i,e_i,p_i)(si​,ei​,pi​)转换成操作即为在[si,ei][s_i,e_i][si​,ei​]区间内加上pip_ipi​的优先级&#xff0c;让后查询的话就是查询第xix_ixi​秒优先级最小的kik_iki​个任务的优先级之和。可知这两个操…

asp.net core 系列之Performance的 Response compression(响应压缩)

本文&#xff0c;帮助了解响应压缩的一些知识及用法(大部分翻译于官网,英文水平有限,不准确之处,欢迎指正)。什么是响应压缩&#xff1f;响应压缩简单的说就是为了减少网络带宽&#xff0c;而把返回的响应压缩&#xff0c;使之体积缩小&#xff0c;从而加快响应的一种技术(个人…

CF1516E. Baby Ehab Plays with Permutations(组合数学)

CF1516E. Baby Ehab Plays with Permutations Solution 因为组合水平不行所以只弄出来一个O(k4)O(k^4)O(k4)的做法&#xff08;虽然随便改改可能就O(k3log⁡k)O(k^3\log k)O(k3logk)或者O(k3)O(k^3)O(k3)了&#xff09;而且因为没想清楚而自闭了很久&#xff0c;从而导致摸yu…

Codeforces Round #603 (Div. 2) E. Editor 线段树维护括号序列

传送门 文章目录题意&#xff1a;思路&#xff1a;题意&#xff1a; 思路&#xff1a; 首先一个括号序列合法的条件可以转化成两个(左括号代价为111&#xff0c;右括号代价为−1-1−1)&#xff1a; (1) 左括号个数等于右括号个数。 (2) 括号的前缀和非负。 所以我们直接用线段…

从ASP.NET Core 3.0 preview 特性,了解CLR的Garbage Collection

前言在阅读这篇文章&#xff1a;Announcing Net Core 3 Preview3的时候&#xff0c;我看到了这样一个特性&#xff1a;Docker and cgroup memory LimitsWe concluded that the primary fix is to set a GC heap maximum significantly lower than the overall memory limit as …