旅游题解树形dp

旅游

https://ac.nowcoder.com/acm/problem/15748

首先题意说的很清楚,必须从一开始,然后去找最长的旅游天数,那么我们可以看出是在一颗树上面操作的,那么就是树形dp来解决,我们可以定义dp[i][1/0],什么意思呢,就是第i个地方我是选择住宿还是不住宿(1/0)的最长停留时间,那么我们如果到了以X为根的节点,如果要住那就是dp[x][1]=dp[y][0]+1,父节点住宿了那么儿子节点必然不可以住宿,然后如果没有住宿是不是就是dp[x][0]+=max(dp[y][1],dp[y][0])

#include <bits/stdc++.h>
#define fio ios_base::sync_with_stdio(0);cin.tie(0);cout.tie(0);
#define debug(x) cout << #x << ": " << x << endl;
#define debug1(x) cout<<"xxx"<<endl;
#define ll long long
#define ull unsigned long long
#pragma GCC optimize("Ofast","inline","-ffast-math")
#pragma GCC target("avx,sse2,sse3,sse4,mmx")
#define mse(a,b) memset(a,b,sizeof a);
#define fro for
#define it int
using namespace std;
const int maxx=1e6+100;
const int mod=1e9+7;
//ll qpow(ll a, ll b) { ll ans = 1;    while (b) { if (b & 1)    ans *= a;        b >>= 1;        a *= a; }    return ans; }    ll qpow(ll a, ll b, ll mod) { ll ans = 1; while (b) { if (b & 1)(ans *= a) %= mod; b >>= 1; (a *= a) %= mod; }return ans % mod; }
//inline ll read() { ll s = 0, w = 1; char ch = getchar(); for (; !isdigit(ch); ch = getchar()) if (ch == '-') w = -1; for (; isdigit(ch); ch = getchar())    s = (s << 1) + (s << 3) + (ch ^ 48); return s * w; }
vector<int>ans[1<<20];
int dp[1<<20][2];
void dfs(int x,int fa)
{
    dp[x][1]=1,dp[x][0]=0;
    for(auto v:ans[x])
    {
        if(v==fa) continue;
        dfs(v,x);
        dp[x][1]+=dp[v][0];
        dp[x][0]+=max(dp[v][1],dp[v][0]);
        // cout<<x<<" "<<dp[x][0]<<" "<<dp[x][1]<<endl;
    }
}
int main()
{
    fio;
    int n,s;
    cin>>n>>s;
    for(int i=1,u,v; i<=n-1; i++)
    {
        cin>>u>>v;
        //u=read(),v=read();
        ans[u].push_back(v);
        ans[v].push_back(u);
    }
    dfs(s,-1);
    cout<<dp[s][1];
    return 0;
}
全部评论

相关推荐

10-07 20:48
门头沟学院 Java
听说改名就会有offer:可能是实习上着班想到后面还要回学校给导师做牛马,看着身边都是21-25的年纪,突然emo了了
点赞 评论 收藏
分享
点赞 收藏 评论
分享
牛客网
牛客企业服务