最大独立集问题是指对于一棵n个结点的无根树,选出尽量多的结点,使得任何两个结点均不相邻,解答过程详见入门经典第二版280页,粘代码跑QAQ
1 #include "iostream" 2 #include "cstdio" 3 #include "cstring" 4 #include "string" 5 #include "vector" 6 using namespace std; 7 const int maxn=1000+10; 8 int n; 9 vector<int> g[maxn]; 10 int son[maxn],gson[maxn]; 11 int f[maxn],dp[maxn],wide[maxn]; 12 int wide_max; 13 void init(){ 14 scanf("%d",&n); 15 for(int i=1;i<n;i++){ 16 int x,y; 17 scanf("%d%d",&x,&y); 18 g[x].push_back(y); 19 g[y].push_back(x); 20 } 21 } 22 void dfs(int v,int fa){ 23 int d=g[v].size(); 24 if(fa==-1) 25 wide[v]=0; 26 else 27 wide[v]=wide[fa]+1; 28 if(wide[v]>wide_max) 29 wide_max=wide[v]; 30 for(int i=0;i<d;i++){ 31 int k=g[v][i]; 32 if(k!=fa) 33 dfs(k,f[k]=v); 34 } 35 } 36 int treedp(int root){ 37 f[root]=-1; 38 wide_max=-1; 39 dfs(root,-1); 40 for(int i=wide_max;i>=0;i--){ 41 for(int j=1;j<=n;j++){ 42 if(wide[j]==i){ 43 dp[j]=max(son[j],gson[j]+1); 44 if(i>=1) 45 son[f[j]]+=dp[j]; 46 if(i>=2) 47 gson[f[f[j]]]+=dp[j]; 48 } 49 } 50 } 51 return dp[root]; 52 } 53 int solve(){ 54 int ans=0; 55 for(int i=1;i<=n;i++){ 56 memset(son,0,sizeof(son)); 57 memset(gson,0,sizeof(gson)); 58 ans=max(ans,treedp(i)); 59 } 60 return ans; 61 } 62 int main() 63 { 64 init(); 65 int ans=solve(); 66 printf("%d\n",ans); 67 return 0; 68 }