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

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

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


2020 ICPC Macau A. Accelerator(分治FFT)

Problem

给定长度为 nnn 的数组 aia_iai​ ,对于 1∼n1\sim n1∼n 的所有的排列 pip_ipi​ ,计算 ((((0+1)∗ap1+1)∗ap2+⋯)+1)∗apn((((0 + 1) *a_{p_1} + 1) * a_{p_2} + \cdots) + 1) * a_{p_n}((((0+1)∗ap1​​+1)∗ap2​​+⋯)+1)∗apn​​ 的期望。

n≤105n\le 10^5n≤105

Solution

显然我们把要求的式子展开以后有:

val=∏i=1napi+∏i=2napi+⋯+∏i=nnapival = \prod\limits_{i = 1}^{n}a_{p_i} + \prod\limits_{i = 2}^{n}a_{p_i} + \cdots + \prod\limits_{i = n}^{n}a_{p_i}val=i=1∏n​api​​+i=2∏n​api​​+⋯+i=n∏n​api​​

考虑对于任意一个排列的乘积,∏inapi\displaystyle\prod\limits_{i}^{n}a_{p_i}i∏n​api​​ ,它自己对于答案期望的贡献。

显然期望等于权值乘以概率,对于一段长度为 iii 的排列,它的概率显然为 i!×(n−i)!n!\cfrac{i!\times (n-i)!}{n!}n!i!×(n−i)!​(iii 个数全排列乘上剩余 n−in-in−i 个数全排列比上总方案数:nnn个数全排列),那么它对答案的贡献显然为 ∏inapi×i!×(n−i)!n!\displaystyle\prod\limits_{i}^{n}a_{p_i}\times \cfrac{i!\times (n-i)!}{n!}i∏n​api​​×n!i!×(n−i)!​

由于期望的可加性,我们发现对于所有的长度为 iii 的排列,它的贡献均为∏inapi×i!×(n−i)!n!\displaystyle\prod\limits_{i}^{n}a_{p_i}\times \cfrac{i!\times (n-i)!}{n!}i∏n​api​​×n!i!×(n−i)!​,所以我们可以把 i!×(n−i)!n!\cfrac{i!\times (n-i)!}{n!}n!i!×(n−i)!​ 提到和式的外面,设 fif_ifi​ 表示剩余的式子,设 SSS 为从 nnn 个数中任取 iii 个数的所有排列的集合,则有:

fi=∑p∈S∏j=1iapjf_i= \displaystyle\sum_{p\in S}\prod\limits_{j=1}^{i}a_{p_{j}} fi​=p∈S∑​j=1∏i​apj​​

显然要求的答案期望 E(x)E(x)E(x) :

E(x)=∑i=1nfi×i!×(n−i)!n!\begin{aligned} E(x)=\displaystyle \cfrac{\displaystyle \sum\limits_{i = 1} ^ {n} f_i\times i! \times (n - i) !}{n!} \end{aligned} E(x)=n!i=1∑n​fi​×i!×(n−i)!​​

也就是我们只需要求出 1∼n1\sim n1∼n 的 fif_ifi​ 即可。

我们知道

fi=∑p∈S∏j=1iapjf_i= \displaystyle\sum_{p\in S}\prod\limits_{j=1}^{i}a_{p_{j}} fi​=p∈S∑​j=1∏i​apj​​

即:

fi=∑j=1ifi−j×fjf_i=\sum_{j=1}^{i}f_{i-j}\times f_j fi​=j=1∑i​fi−j​×fj​

显然就是一个自己卷自己的分治FFT的模板,直接用分治 FFT O(nlog⁡2n)O(n\log^2 n)O(nlog2n) 计算即可,递归的边界设为 aia_iai​。

Hint

CF GNU C++17 (64) = 327 ms,GNU C++17 = 951 ms ∼\sim∼ TLE …

Code

#include <bits/stdc++.h>
using namespace std;
using ll = long long;
const int N = 2e5 + 5, mod = 998244353, P = 998244353, MOD = 998244353;template <typename T> inline void read(T& t) {int f = 0, c = getchar(); t = 0; while (!isdigit(c)) f |= c == '-', c = getchar();while (isdigit(c)) t = t * 10 + c - 48, c = getchar();if (f) t = -t;
}template <typename T> void print(T x) {if (x < 0) x = -x, putchar('-');if (x > 9) print(x / 10);putchar(x % 10 + 48);
}    int RR[N];
int n, m, s, t, k, a[N];
int limit, L , G = 3; int qpow(int a, int b)
{int ans = 1;while(b) {if(b & 1) ans = 1ll * ans * a % mod;a = 1ll * a * a % mod;b >>= 1;}return ans % mod;
}
void NTT(int limit, int *A, int type) {for (int i = 0; i < limit; i ++)if (i < RR[i])swap(A[i], A[RR[i]]); for (int mid = 1; mid < limit; mid <<= 1) {int wn = qpow(G, (mod - 1) / (mid << 1)); for (int pos = 0; pos < limit; pos += (mid << 1)) {int w = 1; for (int k = 0; k < mid; k ++, w = 1ll * w * wn % mod) {int x = A[pos + k], y = 1ll * w * A[pos + mid + k] % mod;A[pos + k] = (x + y) % mod;A[pos + k + mid] = (x - y + mod) % mod;}}} if (type == 1)return ; for (int i = 1; i < limit / 2; i ++)swap(A[i], A[limit - i]); int inv = qpow(limit, mod - 2); for (int i = 0; i < limit; i ++) {A[i] = 1ll * A[i] * inv % mod;}
}
void NTT_mul(int *f, int *g, int *h, int n, int m)
{int limit = 1, L = 0; while(limit <= n + m) limit <<= 1, L ++ ; for (int i = n + 1; i < limit; ++ i) f[i] = 0; for (int i = m + 1; i < limit; ++ i) g[i] = 0; for (int i = 0; i < limit; ++ i)RR[i] = (RR[i >> 1] >> 1) | ((i & 1) << (L - 1));NTT(limit, f, 1), NTT(limit, g, 1); for (int i = 0; i < limit; ++ i)h[i] = 1ll * f[i] * g[i] % mod;  NTT(limit, h, -1);
}     int f[N << 1], g[N << 1], h[N << 1];
int inv[N << 1], fact[N << 1], infact[N << 1];vector<int> solve(int l, int r)
{vector<int> res;if(l == r) {return {1, a[l]};}int mid = (l + r) >> 1;int len1 = mid - l + 1, len2 = r - mid;auto res1 = solve(l, mid);auto res2 = solve(mid + 1, r);for (register int i = 0; i <= len1; ++ i) f[i] = res1[i];for (register int i = 0; i <= len2; ++ i)g[i] = res2[i]; NTT_mul(f, g, h, len1, len2);res.resize(len1 + len2 + 1);for (register int i = 0; i < len1 + len2 + 1; ++ i)  res[i] = h[i]; return res;
} void pre_work(int n)
{inv[0] = inv[1] = 1;for (int i = 2; i <= n; ++ i)  inv[i] = 1ll * (mod - mod / i) * inv[mod % i] % mod;   fact[0] = infact[0] = 1;for (int i = 1; i <= n; ++ i) {fact[i] = 1ll * fact[i - 1] * i % mod;infact[i] = 1ll * infact[i - 1] * inv[i] % mod;}
}int main()
{pre_work(N - 7);read(t);while(t -- ) {read(n);for (register int i = 1; i <= n; ++ i)  read(a[i]); auto res = solve(1, n); int ans = 0;for (register int i = 1;i <= n; ++ i) {ans += 1ll * res[i] * fact[i] % mod * fact[n - i] % mod;if(ans >= mod) ans -= mod;}ans = 1ll * ans * infact[n] % mod;print(ans);puts("");}return 0;
}

%=[x^i]\prod_{j=1}^{n}(1+a_j x)

%显然有f_1=\displaystyle \sum_{i=1}^na_i,f_2=\sum_{j=1}^{2}f_{2-j}\times f_j

2020 ICPC Macau A. Accelerator(期望,计数,分治FFT)(每日一题 21.7.6)相关推荐

  1. 【学习笔记】分治FFT

    整理的算法模板合集: ACM模板 点我看算法全家桶系列!!! 实际上是一个全新的精炼模板整合计划 目录 分治FFT 1. Luogu P4721 [模板]分治 FFT 2. 2020 ICPC Mac ...

  2. UOJ #214 合唱队形 (概率期望计数、DP、Min-Max容斥)

    UOJ #214 合唱队形 (概率期望计数.DP.Min-Max容斥) 9个月的心头大恨终于切掉了!!!! 非常好的一道题,不知为何uoj上被点了70个差评. 题目链接: http://uoj.ac/ ...

  3. 2020 ICPC NAC

    2020 ICPC NAC 题号 题目 知识点 难度 A Another Coin Weighing Puzzle B Mini Battleship C Bomas D All Kill E Gri ...

  4. The 2020 ICPC Asia Shenyang Regional Programming Contest I题 Rise of Shadows(数论)

    题目链接The 2020 ICPC Asia Shenyang Regional Programming Contest 题目大意: 一天内有H小时,每小时M分钟,时针分针以恒定速率旋转. 现在若时针 ...

  5. The 2020 ICPC Asia Yinchuan Regional Programming Contest

    The 2020 ICPC Asia Yinchuan Regional Programming Contest A 开三个vector数组存储x,y,z轴上的点,unique+erase去重 #in ...

  6. 【2020 ICPC Asia East Continent Final】赛前训练

    这里写自定义目录标题 [2020 ICPC Asia East Continent Final]赛前训练 A - Namomo Subsequence 输入: 输出: 样例: 解析: 代码: F - ...

  7. 安卓 每日一题 2020年9-10月问题及答案

    最新 文章连接,本文不再同步 Android9月1日题: 请解释下 Android 程序运行时权限与文件系统权限的区别? 参考答案: apk 程序是运行在虚拟机上的,对应的是 Android 独特的权 ...

  8. (2016北京集训十)【xsy1529】小Q与进位制 - 分治FFT

    题意很简单,就是求这个数... 其实场上我想出了分治fft的正解...然而不会打...然后打了个暴力fft挂了... 没啥好讲的,这题很恶心,卡常卡精度还爆int,要各种优化,有些dalao写的很复杂 ...

  9. [洛谷P4721]【模板】分治 FFT

    题目大意:给定长度为$n-1$的数组$g_{[1,n)}$,求$f_{[0,n)}$,要求: $$ f_i=\sum_{j=1}^if_{i-j}g_j\\ f_0=1 $$ 题解:直接求复杂度是$O ...

最新文章

  1. 浅谈批处理获取管理员运行权限的几种方法
  2. 构建弹性架构组件—ELB和ASG
  3. 【Java 并发编程】线程简介 ( 并发类型 | 线程状态 | CPU 数据缓存 )
  4. python学习(操作列表、if语句)
  5. 5年前面试题引发的“血案”(番外篇)(总结和乱侃)
  6. 系统弹出菜单类名是固定的. #32769
  7. 你准备好了在云中工作吗?
  8. php滴滴平台接口,图片服务API文档
  9. c++获取输入数字的位数/获取位数并且将其存入数组中/获取位数存入数组并且利用它解决实际问题
  10. 利用VisualVm和JMX远程监控K8S里的Java进程
  11. Python福彩3D单选单复式排列计算器
  12. php 抽奖活动_php 实现活动人选抽奖功能代码
  13. android+浮层布局,如何使用Android实现单页面浮层可拖动view
  14. Segmentation fault (core dumped) 和double free or corruption (out)Aborted (core dumped)
  15. 6个自学python必看网站
  16. FFMpeg.AutoGen(1)讲解官方example代码:Main函数、 解码
  17. 【DKN】(一)KCN详解
  18. 内部类有哪些好处?什么时候使用内部类
  19. HTML5 学习总结(四)——canvas绘图、WebGL、SVG
  20. 人大金仓 日常命令 已解决

热门文章

  1. CMake编译工具与项目构建
  2. 【小白学PyTorch】4.构建模型三要素与权重初始化
  3. 三分钟教你快速选择机器视觉传感器
  4. 《机器学习》、《算法数据结构》、《LeetCode原创题解》开放下载!
  5. 22.加密与安全相关,证书申请CA(gpg,openssl)
  6. select * 和 select 所有字段的区别
  7. Kotlin学习笔记(五) 扩展函数 扩展属性
  8. 英文版windows乱码问题(win7/8/10)
  9. 恩布企业IM,协同办公平台发布V1.24.2版本
  10. Axis2 客户端调用 设置超时时间