HDU 5829 Rikka with Subset(NTT)
题意
给定 \(n\) 个数 \(a_1,a_2,\cdots a_n\),对于每个 \(K\in[1,n]\) ,求出 \(n\) 个数的每个子集的前 \(K\) 大数的和,输出每个值,对 \(998244353\) 取模。
\(1\leq n \leq 10^5\)
思路
设 \(K\) 为 \(k\) 时的答案为 \(ans_k\)
有
\]
\(j\) 为在 \(a_i\) 的左边选了多少个数。定义当\(i<j\) 时 \(\displaystyle{i\choose j}=0\) ,即当 \(n<0\) 时 \(\displaystyle{1\over n!}=0\)
有两个\(\sum\) ,导致难以化简,但是我们发现差分后只有一个 \(\sum\)
设 \(d_k=ans_k-ans_{k-1}\) ,则有
d_k=(k-1)!\sum_{i=1}^na_i2^{n-i}(i-1)!\cdot{1\over{(i-k)!}}
\]
用 \(i+k\) 替换 \(k\) ,并化成卷积形式
\]
其中 \(i\in[1,n],i+k\in[1,n],k\in[1-n,n-1]\)
设 \(\displaystyle A_i=a_i2^{n-i}(i-1)!,B_k={1\over{(-k)!}}\)
\(d_{i+k}=(i+k-1)A_iB_k\)
处理出 \(A,B\) 两多项式,进行卷积求解即可。
代码
#include<bits/stdc++.h>
#define FOR(i,x,y) for(int i=(x),i##END=(y);i<=i##END;++i)
#define DOR(i,x,y) for(int i=(x),i##END=(y);i>=i##END;--i)
typedef long long ll;
using namespace std;
const int P=998244353,g=3;
const int N=1<<17|5;
namespace Maths
{
ll gcd(ll a,ll b){return b?gcd(b,a%b):a;}
void exgcd(ll a,ll b,ll &x,ll &y)
{
if(!b){x=1,y=0;return;}
exgcd(b,a%b,y,x),y-=a/b*x;
}
ll Pow(ll a,ll p,ll P)
{
ll res=1;
for(;p>0;p>>=1,(a*=a)%=P)if(p&1)(res*=a)%=P;
return res;
}
ll inv(ll a,ll P){ll x,y;exgcd(a,P,x,y);return (x%P+P)%P;}
};
using namespace Maths;
namespace _NTT
{
const int g=3,P=998244353;
int A[N<<1],B[N<<1];
int w[N<<1],r[N<<1];
void NTT(int *a,int op,int n)
{
FOR(i,0,n-1)if(i<r[i])swap(a[i],a[r[i]]);
for(int i=2;i<=n;i<<=1)
for(int j=0;j<n;j+=i)
for(int k=0;k<i/2;k++)
{
int u=a[j+k],t=(ll)w[op==1?n/i*k:n-n/i*k]*a[j+k+i/2]%P;
a[j+k]=(u+t)%P;
a[j+k+i/2]=(u-t)%P;
}
}
void multiply(int *a,int *b,int *c,int n1,int n2)
{
int n=1;
while(n<n1+n2-1)n<<=1;
FOR(i,0,n1-1)A[i]=a[i];
FOR(i,0,n2-1)B[i]=b[i];
FOR(i,n1,n-1)A[i]=0;
FOR(i,n2,n-1)B[i]=0;
FOR(i,0,n-1)r[i]=(r[i>>1]>>1)|((i&1)*(n>>1));
w[0]=1,w[1]=Pow(g,(P-1)/n,P);
FOR(i,2,n)w[i]=(ll)w[i-1]*w[1]%P;
NTT(A,1,n),NTT(B,1,n);
FOR(i,0,n-1)A[i]=(ll)A[i]*B[i]%P;
NTT(A,-1,n);
int I=inv(n,P);
FOR(i,0,n1+n2-2)c[i]=((ll)A[i]*I%P+P)%P;
}
};
int A[N],B[N],C[N<<2];
int fac[N],c[N],S;
int n,m;
int main()
{
fac[0]=1;FOR(i,1,N-1)fac[i]=(ll)fac[i-1]*i%P;
while(~scanf("%d",&n))
{
FOR(i,0,n)scanf("%d",&c[i]);
scanf("%d",&m);
S=0;
while(m--)
{
int x;
scanf("%d",&x);
S-=x;
if(S<0)S+=P;
}
FOR(i,0,n)A[i]=(ll)c[i]*fac[i]%P;
FOR(i,-n,0)B[i+n]=Pow(S,-i,P)*inv(fac[-i],P)%P;
_NTT::multiply(A,B,C,n+1,n+1);
FOR(i,0,n)printf("%lld ",(C[i+n]*inv(fac[i],P)%P+P)%P);
puts("");
}
return 0;
}
HDU 5829 Rikka with Subset(NTT)的更多相关文章
- HDU - 5829:Rikka with Subset (NTT)
As we know, Rikka is poor at math. Yuta is worrying about this situation, so he gives Rikka some mat ...
- HDU 6092 Rikka with Subset(dp)
http://acm.hdu.edu.cn/showproblem.php?pid=6092 题意: 给出两个数组A和B,A数组一共可以有(1<<n)种不同的集合组合,B中则记录了每个数出 ...
- hdu 6092 Rikka with Subset(逆向01背包+思维)
Rikka with Subset Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 65536/65536 K (Java/Others ...
- 2017 ACM暑期多校联合训练 - Team 5 1008 HDU 6092 Rikka with Subset (找规律)
题目链接 Problem Description As we know, Rikka is poor at math. Yuta is worrying about this situation, s ...
- HDU 6088 Rikka with Rock-paper-scissors(NTT+欧拉函数)
题意 \(n\) 局石头剪刀布,设每局的贡献为赢的次数与输的次数之 \(\gcd\) ,求期望贡献乘以 \(3^{2n}\) ,定义若 \(xy=0\) 则,\(\gcd(x,y)=x+y\) 思路 ...
- hdu 6092 Rikka with Subset(多重背包)
题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=6092 #include <cstdio> #include <iostream> ...
- hdu 5423 Rikka with Tree(dfs)
Problem Description As we know, Rikka is poor at math. Yuta is worrying about this situation, so he ...
- hdu 5423 Rikka with Tree(dfs)bestcoder #53 div2 1002
题意: 输入一棵树,判断这棵树在以节点1为根节点时,是否是一棵特殊的树. 相关定义: 1. 定义f[A, i]为树A上节点i到节点1的距离,父节点与子节点之间的距离为1. 2. 对于树A与树B,如 ...
- hdu 5631 Rikka with Graph(图)
n个点最少要n-1条边才能连通,可以删除一条边,最多删除2条边,然后枚举删除的1条边或2条边,用并查集判断是否连通,时间复杂度为O(n^3) 这边犯了个错误, for(int i=0;i<N;i ...
随机推荐
- Toolkit tool 获取屏幕、显示在屏幕中心
2018-11-11 15:30:05开始写 Toolkit tool = Toolkit.getDefaultToolkit(); Dimension d = tool.getScreenSize ...
- jQuery选择器--selector1,selector2,selectorN和ancestor descendant
selector1,selector2,selectorN 概述 将每一个选择器匹配到的元素合并后一起返回.你可以指定任意多个选择器,并将匹配到的元素合并到一个结果内 参数 selector1 ...
- Linux服务器---流量监控ntop
Ntop Ntop 是一款类似于sniffer的流量监控工具,它显示出的流量信息比mrtg更加详细. 1 .安装一些依赖软件 [root@localhost bandwidthd]# yum ins ...
- JS实现input中输入数字,控制每四位加一个空格(银行卡号格式)
前言 今天来讲讲js中实现input中输入数字,控制每四位加一个空格的方法!这个主要是应用于我们在填写表单的时候,填写银行卡信息,要求我们输入的数字是四位一个空格!今天主要介绍两种方式来实现这个方法! ...
- 系统调用号、errno
最近老需要看系统调用号,errno,所以这里记一下 CentOS Linux release 7.2.1511 (Core) 3.10.0-327.el7.x86_64 [root@localhost ...
- Git在Eclipse中的使用
一.把远程仓库的项目clone到eclipse里面: 最新版的Eclipse上已经集成了Git插件.所以在Eclipse中可以很方便的使用Git的功能. 在使用Git功能之前,需要先进行下简单的设置. ...
- 【linux应用】将一个大文件按行拆分成小文件
例如将一个BLM.txt文件分成前缀为 BLM_ 的1000个小文件,后缀为系数形式,且后缀为4位数字形式 先利用 wc -l BLM.txt #读出BLM.txt有多少行. 再利用 split 命令 ...
- maven 项目 查询部分关心的字段
<?xml version="1.0" encoding="UTF-8" ?> <!DOCTYPE configuration PUBLIC ...
- USB设备被识别流程
源: USB设备被识别流程
- 关于scrapy下载文件重命名的办法以及对应url没有文件后缀的办法
https://www.jianshu.com/p/d1bb28cbb6a8 scrapy中负责下载文件的是class MyFilesPipeline(FilesPipeline)类 其中负责下载文件 ...