老师发福利,放了两道一毛一样的题。
考虑无视战术,直接化简:
\[\sum_{v=1}^ndis(u,v)^k=\sum_{v=1}^n\sum_{i=0}^k\begin{Bmatrix}k\\i\end{Bmatrix}dis(u,v)^\underline i
\]
\[=\sum_{i=0}^k\begin{Bmatrix}k\\i\end{Bmatrix}\sum_{v=1}^ndis(u,v)^\underline i
\]
\[=\sum_{i=0}^k\begin{Bmatrix}k\\i\end{Bmatrix}\sum_{v=1}^ni!\binom{dis(u,v)}i
\]
\[=\sum_{i=0}^k\begin{Bmatrix}k\\i\end{Bmatrix}i!\sum_{v=1}^n\binom{dis(u,v)}i
\]
\[=\sum_{i=0}^k\begin{Bmatrix}k\\i\end{Bmatrix}i!\sum_{v=1}^n\binom{dis(u,v)-1}i+\binom{dis(u,v)-1}{i-1}
\]
为什么要进行最后一步分解呢?这和接下来的推导有关系。
实际上推到这里已经不用再推了,我们只需要能求出 \(f_{u,i}=\sum\limits_{v=1}^n\binom{dis(u,v)}i\) 就可以了。考虑换根 \(dp\)。
首先显然有:
\[f_{u,0}=1+\sum_{v\in son(u)}f_{v,0}
\]
对于 \(i>0\) 的情况,我们可以使用最后一步的推导。考虑最后一步 \(dis(u,v)-1\) 相当于是把问题转化到了儿子上,即:
\[f_{u,i}=\sum_{v\in son(u)}f_{v,i-1}+f_{v,i}
\]
换根 \(dp\),时间复杂度 \(O(nk)\)。
#include<bits/stdc++.h>
using namespace std;
const int N=155,M=50005,p=10007;
int str[N][N],f[M][N],g[M][N],ans;
vector<int>ve[M];int n,k,l,nw,aa,bb,q;
void dfs1(int x,int fa){for(auto y:ve[x]){if(y==fa) continue;dfs1(y,x);f[x][0]=(f[x][0]+f[y][0])%p;for(int i=1;i<=k;i++)f[x][i]=(f[x][i]+f[y][i]+f[y][i-1])%p;}f[x][0]++;
}void dfs2(int x,int fa){if(x!=1){for(int i=1;i<=k;i++){g[x][i]+=g[fa][i]+g[fa][i-1]+f[fa][i];g[x][i]+=f[fa][i-1]-f[x][i]-2*f[x][i-1];if(i>1) g[x][i]-=f[x][i-2];g[x][i]%=p;}g[x][0]=(g[fa][0]+f[fa][0]-f[x][0]+p)%p;}for(auto y:ve[x])if(y!=fa) dfs2(y,x);
}int main(){ios::sync_with_stdio(0);cin.tie(0),cout.tie(0);cin>>n>>k>>l>>nw>>aa>>bb>>q,str[0][0]=1;for(int i=1;i<n;i++){nw=(nw*aa+bb)%q;int tmp=(i<l?i:l);int x=i-nw%tmp,y=i+1;ve[x].push_back(y);ve[y].push_back(x);}for(int i=1;i<=k;i++) for(int j=1;j<=i;j++)str[i][j]=(str[i-1][j-1]+str[i-1][j]*j)%p;dfs1(1,0),dfs2(1,0);for(int j=1;j<=n;j++,ans=0){for(int i=0,jc=1;i<=k;i++,jc=jc*i%p){int now=str[k][i]*jc%p;ans=(ans+now*(f[j][i]+g[j][i]))%p;}cout<<(ans+p)%p<<"\n";}return 0;
}