注意两点就是dp[x][0]=1;代表这个x点要选,dp[x][k+1]=1;代表这个数不图成黑色,就是这个样子。还是应该脑子转的快一点,我感觉这种问题思考起来不是那么的难。#include<bits/stdc++.h>
using namespace std;
const int mod=1e9+7;
int n,m;
long long dp[1000][199];
long long f[1000];
vector<int>v[1000];
int vis[1000];
void dfs(int x,int pre)
{
vis[x]=1;
dp[x][0]=1;
dp[x][m+1]=1;
int sz=v[x].size();
for(int o=0;o<sz;o++)
{
int y=v[x][o];
if(vis[y]) continue;
dfs(y,x);
memset(f,0,sizeof(f));
for(int i=0;i<=2*m;i++)
{
for(int j=0;j<=2*m;j++)
{
if(i+j<=2*m)
{
f[min(i,j+1)]+=(dp[x][i]%mod*dp[y][j]%mod)%mod;
f[min(i,j+1)]=f[min(i,j+1)]%mod;
}
else
{
f[max(i,j+1)]+=(dp[x][i]%mod*dp[y][j]%mod)%mod;
f[max(i,j+1)]=f[max(i,j+1)]%mod;
}
}
}for(int i=0;i<=2*m;i++)
{
dp[x][i]=f[i];
}
}
}
int main()
{
scanf("%d%d",&n,&m);
for(int i=1;i<n;i++)
{
int a,b;
scanf("%d%d",&a,&b);
v[a].push_back(b);
v[b].push_back(a);
}
dfs(1,0);
long long ans=0;
for(int i=0;i<=m;i++)
{
ans+=dp[1][i]%mod;
ans=ans%mod;
}
cout<<ans<<endl;
}
本文介绍了一种基于图论的动态规划算法实现方法,通过递归深度优先搜索遍历图结构,并利用动态规划记录每一步的选择状态,最终求解特定节点的所有合法子集的方案数。文章提供了一个完整的C++代码示例。
6457

被折叠的 条评论
为什么被折叠?



