树形dp——Tree2cycle

一、问题描述(题目链接

给你一棵树,删除或添加一条边的费用都是1,问使它变成一个环的最小费用。

二、解题思路

回溯法,然后回溯的时候的当前节点度数>2(如果是成环的话肯定就是2或者小于2)就把它和父节点之间的边砍掉。每砍掉一次,以后是要连上的,只需乘2就行。由于是回溯回来的,父节点在子节点阶段就考虑了一次,相当于与该子节点与父节点没有边了,所以父节点的度数减1。

三、代码实现

 1 #include<stdio.h>
 2 #include<iostream>
 3 #include<algorithm>
 4 #include<cstring>
 5 #include<vector>
 6 using namespace std;
 7 
 8 const int maxn = 1000000 + 10;
 9 vector<int>G[maxn];
10 int degree[maxn],ans,n;
11 
12 void init()
13 {
14     ans = 0;
15     memset(degree, 0, sizeof(degree));
16     for (int i = 0; i <= n; i++)
17         G[i].clear();
18 }
19 
20 void dfs(int son, int fa)
21 {
22     int k = G[son].size();
23     for (int i = 0; i < k; i++)
24     {
25         int newson = G[son][i];
26         if (newson == fa)    continue;
27         dfs(newson, son);
28         if (degree[newson] > 2)
29         {
30             degree[son]--;                //父节点要减一
31             ans += (degree[newson] - 2) * 2;
32         }
33     }
34 }
35 
36 int main()
37 {
38     int T;
39     scanf("%d", &T);
40     while (T--)
41     {
42         int a, b;
43         init();
44         scanf("%d", &n);
45         for (int i = 1; i < n; i++)
46         {
47             scanf("%d%d", &a, &b);
48             degree[a]++;
49             degree[b]++;
50             G[a].push_back(b);
51             G[b].push_back(a);
52         }
53         int root = 1;
54         for (int i = 1; i <= n; i++)    //找到度数为一的节点作为根节点,开始搜索
55         {
56             if (degree[i] == 1)
57             {
58                 root = i;
59                 break;
60             }
61         }
62         dfs(root, 0);
63         printf("%d\n", ans + 1);
64     }
65     return 0;
66 }

 

转载于:https://www.cnblogs.com/lfri/p/9485503.html

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值