【BZOJ2159】Crash的文明世界(第二类斯特林数,动态规划)
【BZOJ2159】Crash的文明世界(第二类斯特林数,动态规划)
题面
题解
看到\(k\)次方的式子就可以往二项式的展开上面考,但是显然这样子的复杂度会有一个\(O(k^2)\),因此需要换别的方法。
注意到自然指数幂和第二林斯特林数之间的关系:
\]
那么将答案式化简
Ans_x&=\sum_{i=1}^N dis(i,x)^K\\
&=\sum_{i=1}^N \sum_{j=0}^K \begin{Bmatrix}K\\j\end{Bmatrix}{dis(x,i)\choose j}j!\\
&=\sum_{j=0}^K\begin{Bmatrix}K\\j\end{Bmatrix}j!\sum_{i=1}^N {dis(x,i)\choose j}
\end{aligned}\]
那么对于每一个点\(x\),要求的只有\(\displaystyle \sum_{i=1}^N {dis(x,i)\choose j}\)
我们知道组合数杨辉三角上的转移\(\displaystyle {n\choose m}={n-1\choose m}+{n-1\choose m-1}\)
那么带进去,可以得到:$$\sum_{i=1}^N {dis(x,i)\choose j}=\sum_{i=1}^N {dis(x,i)-1\choose j}+\sum_{i=1}^N {dis(x,i)-1\choose j-1}$$
考虑怎么\(dp\),设\(f[i][j]\)表示\(i\)子树内的\({dis\choose j}\)的和。
考虑节点\(u\)和其儿子\(v\)。显然\(v\)的子树到\(u\)的距离是到\(v\)的距离\(-1\)。
所以可以得到转移\(\displaystyle f[u][j]=\sum_{v}(f[v][j]+f[v][j-1])\)。
因为需要换根\(dp\),所以再额外考虑清楚如何减去一个子树的贡献,这里懒得写了。
那么只需要换根\(dp\)做完之后求出所有节点的\(f\),再预处理第二类斯特林数直接算答案即可。
BZOJ数据有点奇怪,用注释的部分读入
#include<iostream>
#include<cstdio>
#include<cstdlib>
#include<cstring>
#include<cmath>
#include<algorithm>
#include<vector>
using namespace std;
#define MOD 10007
#define MAX 50500
#define MAXK 155
inline int read()
{
int x=0;bool t=false;char ch=getchar();
while((ch<'0'||ch>'9')&&ch!='-')ch=getchar();
if(ch=='-')t=true,ch=getchar();
while(ch<='9'&&ch>='0')x=x*10+ch-48,ch=getchar();
return t?-x:x;
}
struct Line{int v,next;}e[MAX<<1];
int h[MAX],cnt=1;
inline void Add(int u,int v){e[cnt]=(Line){v,h[u]};h[u]=cnt++;}
int S[MAXK][MAXK],jc[MAXK];
int f[MAX][MAXK],g[MAX][MAXK],tmp[MAXK];
int n,K;
void dfs(int u,int ff)
{
f[u][0]=1;
for(int i=h[u];i;i=e[i].next)
{
int v=e[i].v;if(v==ff)continue;
dfs(v,u);
for(int j=0;j<=K;++j)f[u][j]=(f[u][j]+f[v][j])%MOD;
for(int j=1;j<=K;++j)f[u][j]=(f[u][j]+f[v][j-1])%MOD;
}
}
void DFS(int u,int ff)
{
for(int j=0;j<=K;++j)g[u][j]=f[u][j];
if(ff)
{
for(int j=0;j<=K;++j)tmp[j]=g[ff][j];
for(int j=0;j<=K;++j)tmp[j]=(tmp[j]+MOD-f[u][j])%MOD;
for(int j=1;j<=K;++j)tmp[j]=(tmp[j]+MOD-f[u][j-1])%MOD;
for(int j=0;j<=K;++j)g[u][j]=(g[u][j]+tmp[j])%MOD;
for(int j=1;j<=K;++j)g[u][j]=(g[u][j]+tmp[j-1])%MOD;
}
for(int i=h[u];i;i=e[i].next)
if(e[i].v!=ff)DFS(e[i].v,u);
}
int main()
{
/*
int L,now,A,B,Q;
scanf("%d%d%d%d%d%d%d",&n,&K,&L,&now,&A,&B,&Q);
for(int i=1;i<n;i++)
{
now=(now*A+B)%Q;
int tmp=i<L?i:L;
int x=i-now%tmp,y=i+1;
Add(x,y);
}
*/
n=read();K=read();
for(int i=1;i<n;++i)
{
int u=read(),v=read();
Add(u,v);Add(v,u);
}
S[0][0]=jc[0]=1;
for(int i=1;i<=K;++i)jc[i]=jc[i-1]*i%MOD;
for(int i=1;i<=K;++i)
for(int j=1;j<=i;++j)
S[i][j]=(S[i-1][j-1]+j*S[i-1][j])%MOD;
dfs(1,0);DFS(1,0);
for(int i=1;i<=n;++i)
{
int ans=0;
for(int j=0;j<=K;++j)
ans=(ans+1ll*S[K][j]*jc[j]*g[i][j])%MOD;
printf("%d\n",ans);
}
return 0;
}
【BZOJ2159】Crash的文明世界(第二类斯特林数,动态规划)的更多相关文章
- [国家集训队] Crash 的文明世界(第二类斯特林数)
题目 [国家集训队] Crash 的文明世界 前置 斯特林数\(\Longrightarrow\)斯特林数及反演总结 做法 \[\begin{aligned} ans_x&=\sum\limi ...
- BZOJ 2159: Crash 的文明世界 第二类斯特林数+树形dp
这个题非常巧妙啊~ #include <bits/stdc++.h> #define M 170 #define N 50003 #define mod 10007 #define LL ...
- bzoj 2159 Crash 的文明世界 && hdu 4625 JZPTREE ——第二类斯特林数+树形DP
题目:https://www.lydsy.com/JudgeOnline/problem.php?id=2159 学习材料:https://blog.csdn.net/litble/article/d ...
- P4827 [国家集训队] Crash 的文明世界(第二类斯特林数+树形dp)
传送门 对于点\(u\),所求为\[\sum_{i=1}^ndis(i,u)^k\] 把后面那堆东西化成第二类斯特林数,有\[\sum_{i=1}^n\sum_{j=0}^kS(k,j)\times ...
- 国家集训队 Crash 的文明世界(第二类斯特林数+换根dp)
题意 题目链接:https://www.luogu.org/problem/P4827 给定一棵 \(n\) 个节点的树和一个常数 \(k\) ,对于树上的每一个节点 \(i\) ,求出 \( ...
- BZOJ 2159: Crash 的文明世界(组合数学+第二类斯特林数+树形dp)
传送门 解题思路 比较有意思的一道数学题.首先\(n*k^2\)的做法比较好想,就是维护一个\(x^i\)这种东西,然后转移的时候用二项式定理拆开转移.然后有一个比较有意思的结论就是把求\(x^i\) ...
- BZOJ2159 Crash的文明世界——树上DP&&第二类Stirling数
题意 给定一个有 $n$ 个结点的树,设 $S(i)$ 为第 $i$ 个结点的“指标值”,定义为 $S(i)=\sum_{i=1}^{n}dist(i,j)^k$,$dist(i, j)$ 为结点 $ ...
- 题解 [BZOJ2159] Crash的文明世界
题面 解析 这题一眼换根DP啊 首先,我们考虑一下如何转换\(n^m\)这个式子, 先把式子摆出来吧:\(n^m=\sum_{j=0}^mS(m,j)C_n^jj!\) 其中\(S(m,j)\)表示第 ...
- 【BZOJ5093】图的价值(第二类斯特林数,组合数学,NTT)
[BZOJ5093]图的价值(第二类斯特林数,组合数学,NTT) 题面 BZOJ 题解 单独考虑每一个点的贡献: 因为不知道它连了几条边,所以枚举一下 \[\sum_{i=0}^{n-1}C_{n-1 ...
随机推荐
- C#去除字符串中的反斜杠
如下,可以使用C#的Replace()方法来替换,但有一点需要注意的是backslash(反斜杠)是特殊字符. string s = "[\"aaaaaaaaaaaaaaaaaaa ...
- Angularjs演示Service功能
在angularjs中,我们可以自定义自己的service.可以说得是自定义的方法,函数. 下面我们一步一步来演示吧:首先为angularjs定义一个app: var demoApp = angula ...
- pycharm shortcut
Alt+F12 is a shortcut to open/hide Terminal panel
- Ionic2 调用Custom Cordova Plugin方法
APP升级到Ionic2之后,如何调用自己写的pulgin,一直测试不成功,现记录这一经过. plugin目前可以分为3类,A类是ionic-native自带的,可以直接导入Typescript类,直 ...
- GlusterFS分布式存储系统中更换故障Brick的操作记录
前面已经介绍了GlusterFS分布式存储集群环境部署记录,现在模拟下更换故障Brick的操作: 1)GlusterFS集群系统一共有4个节点,集群信息如下: 分别在各个节点上配置hosts.同步好系 ...
- Centos6.9下安装并使用VNC的操作记录
VNC是一个的"远程桌面"工具.,通常用于“图形界面”的方式登录服务器,可视化操作.废话不多说了,操作记录如下: 1)安装桌面环境 [root@vm01 ~]# yum -y gr ...
- Jmeter-使用Ultimate Thread Group插件来设置负载场景
前言: Jmeter插件相关请移步:https://www.jianshu.com/p/130c7fddeddf 自定义线程组:jp@gc - Ultimate Thread Group,功能强大,可 ...
- HDOJ2099_整数的尾数
一道我以为不会这么简单,然后暴力盲打竟然给过了的题. HDOJ2099_整数的尾数 #include<stdio.h> #include<stdlib.h> #include& ...
- IP工具类
import org.slf4j.Logger; import org.slf4j.LoggerFactory; import javax.servlet.http.HttpServletReques ...
- Eclipse的Jar包解压出System.js里String与Boolean定义分号可有可无吗?
Eclipse的Jar包解压出System.js里String与Boolean定义分号可有可无吗? org.eclipse.wst.jsdt.core_1.3.300.v201410221502\li ...