题意:给你一个树,问你最少连几条边可以让树中的每一个节点在且只在一个环内。如果无法完成就输出-1。
我们设dp[i][0]为根节点为i的树变成每一个节点都在且只在一个环里所需要的最小边数。dp[i][1]为除了根节点i外其他点都在且只在一个环里所需要的最小边数。
dp[i][2]为除了根节点和一个子节点(以及子节点可有可无的链)都在且只在一个环里所需要的最小边数。
这样我们的状态转移需要考虑以下4种情况:
(第一张图最上面应该是dp[i][1] 当时写错了不好改)
具体代码如下:
#include#include using namespace std;#define ll long longconst ll inf=100000000;ll dp[105][3];vector a[105];void solve(int u,int f){ int i,j; if(a[u].size()==1&&a[u][0]==f) { dp[u][0]=inf; dp[u][1]=0; dp[u][2]=inf; // return; } for(i=0;i >n; for(i=0;i >x>>y; a[x].push_back(y); a[y].push_back(x); } for(i=1;i<=n;i++) for(j=0;j<=2;j++) dp[i][j]=inf; solve(1,-1); ll ans=inf; ans=dp[1][0]; if(ans==inf) cout<<"-1"<