【JZOJ 6080】【GDOI2019模擬2019.3.23】IOer

Description

m種物品,第i種物品的權值爲(ui+v)(ui+v),每種物品有無數個,一種取法的代價爲所取物品權值乘積,
問取n個物品的所有不同取法的代價和,
兩個取法不同當且僅當存在一種物品在兩個方案中取得數量不同,

n1018,m2105,mo=109+7n\leq10^{18},m\leq 2*10^5,mo=10^9+7

Solution

顯然的,我們要求這個東西的第n項:
i=1m(j=0(vi+u)jxj)\prod_{i=1}^m(\sum_{j=0}(vi+u)^jx^j)
生成函數寫出來:
ans=[xn]i=1m11(vi+u)xans=[x_n]\prod_{i=1}^m\frac{1}{1-(vi+u)x}
先拋出結論(下面的構造過程就是證明):存在以下等式
pi=(vi+u)p_i=(vi+u)
i=1m11pix=1(vx)m1i=1mai1pix\prod_{i=1}^m\frac{1}{1-p_ix}=\frac{1}{(vx)^{m-1}}\sum_{i=1}^m\frac{a_i}{1-p_ix}
其中aia_i爲係數,

還有一個東西:1a1b=(1a1b)1ba\frac{1}{a}*\frac{1}{b}=(\frac{1}{a}-\frac{1}{b})\frac{1}{b-a}

考慮增量構造,每次乘上一個11pix\frac{1}{1-p_ix},考慮係數aia_i的變化
爲了方便,我們設加入第j個元素後第i位的係數爲aj,ia_{j,i}
當前我們加入第j位:
(vx)j+1(i=1j1aj1,i1pix)(11pjx)(vx)^{-j+1}(\sum_{i=1}^{j-1}\frac{a_{j-1,i}}{1-p_ix})(\frac{1}{1-p_jx})

(vx)j+1i=1j1(aj1,i11pix11pjx)(vx)^{-j+1}\sum_{i=1}^{j-1}(a_{j-1,i}*\frac{1}{1-p_ix}*\frac{1}{1-p_jx})
用上面那個東西拆開:

(vx)j+1i=1j1aj1,i(11pix11pjx)(1(pipj)x)(vx)^{-j+1}\sum_{i=1}^{j-1}a_{j-1,i}(\frac{1}{1-p_ix}-\frac{1}{1-p_jx})(\frac{1}{(p_i-p_j)x})
把最後面的p拆開:
(vx)j+1i=1j1aj1,i(11pix11pjx)(1(ij)vx)(vx)^{-j+1}\sum_{i=1}^{j-1}a_{j-1,i}(\frac{1}{1-p_ix}-\frac{1}{1-p_jx})(\frac{1}{(i-j)vx})
再把最後面那個的1vx\frac{1}{vx}提到前面,並把剩下的乘進去:

(vx)ji=1j1aj1,i(ji)11pix+aj1,i(ji)11pjx(vx)^{-j}\sum_{i=1}^{j-1}\frac{a_{j-1,i}}{-(j-i)}\frac{1}{1-p_ix}+\frac{a_{j-1,i}}{(j-i)}\frac{1}{1-p_jx}
我們發現一開始的項又出來了,也就是aj1a_{j-1}aja_j之間存在以下關係:
aj,i=1(ji)aj1,ii<ja_{j,i}=-\frac{1}{(j-i)}*a_{j-1,i},當i<j
aj,i=k=1j11(jk)aj1,ki=ja_{j,i}=\sum_{k=1}^{j-1}\frac{1}{(j-k)}*a_{j-1,k},當i=j
也就是對於j>kj>k,有:
aj,i=ak,il=kj11(jl)=ak,i(1)jk(jk)!a_{j,i}=a_{k,i}*\prod_{l=k}^{j-1}-\frac{1}{(j-l)}=a_{k,i}*\frac{(-1)^{j-k}}{(j-k)!}
我們設fi=ai,if_i=a_{i,i},即i這一項第一次出現時的值,有:
fi=j=1i11(ij)ai1,j=j=1i1fj(1)ij1(ij)!f_i=\sum_{j=1}^{i-1}\frac{1}{(i-j)}*a_{i-1,j}=\sum_{j=1}^{i-1}f_j*\frac{(-1)^{i-j-1}}{(i-j)!}

不難發現,f就是個卷積式,也就是:
f=f(i=1(1)i1i!)f=f*(\sum_{i=1}\frac{(-1)^{i-1}}{i!})
寫成生產函數的形式:(一次項記得加上)
f=f(1ex)+xf=f*(1-e^{-x})+x
解得:
f=xexf=xe^x
也就是:
fi=1(i1)!f_i=\frac{1}{(i-1)!}
解出了ff剩下的就好辦了,直接算即可,

1(vx)m1i=1m(1)mi(i1)!(mi)!11pix\frac{1}{(vx)^{m-1}}\sum_{i=1}^m\frac{(-1)^{m-i}}{(i-1)!(m-i)!}*\frac{1}{1-p_ix}

複雜度:O(nlog(109))O(n\log(10^9))

Code

#include <cstdio>
#include <algorithm>
#include <iostream>
#define fo(i,a,b) for(int i=a;i<=b;++i)
#define fod(i,a,b) for(int i=a;i>=b;--i)
#define efo(i,q) for(int i=A[q];i;i=B[i][0])
#define min(q,w) ((q)>(w)?(w):(q))
#define max(q,w) ((q)<(w)?(w):(q))
using namespace std;
typedef long long LL;
const int N=200500,mo=998244353;
int read(int &n)
{
	char ch=' ';int q=0,w=1;
	for(;(ch!='-')&&((ch<'0')||(ch>'9'));ch=getchar());
	if(ch=='-')w=-1,ch=getchar();
	for(;ch>='0' && ch<='9';ch=getchar())q=q*10+ch-48;n=q*w;return n;
}
int m,ans;
LL n,K,nw;
LL f[N];
LL jc[N],jcn[N];
LL ksm(LL q,LL w)
{
	LL ans=1;
	for(;w;w>>=1,q=q*q%mo)if(w&1)ans=ans*q%mo;
	return ans;
}
int main()
{
	freopen("ioer.in","r",stdin);
	freopen("ioer.out","w",stdout);
	int q,w,_;
	n=2e5;
	jc[0]=1;fo(i,1,n)jc[i]=jc[i-1]*i%mo;
	jcn[n]=ksm(jc[n],mo-2);fod(i,n-1,0)jcn[i]=jcn[i+1]*(i+1LL)%mo;
	read(_);
	while(_--)
	{
		scanf("%lld%d%lld%lld",&n,&m,&K,&nw);
		ans=0;
		fo(i,1,m)
		{
			nw=(nw+K)%mo;
			f[i]=jcn[i-1]*jcn[m-i]%mo*((m-i)&1?-1:1);
			ans=(ans+f[i]*ksm(nw,n+m-1))%mo;
		}
		ans=ans*ksm(ksm(K,m-1),mo-2)%mo;
		printf("%lld\n",(ans+mo)%mo);
	}
	return 0;
}
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章