Information Disturbing 【HDU - 3586】【树形DP+二分答案】

题目链接

之前写了纯的树形DP,现在用一下二分来进行优化

我二分中设定的答案为限制,就是最多能剪去价值为mid的枝,并且所有的子枝之和也要不大于mid,然后判断最后的dp[1]是否“<=M”即可。

这里有一个细节,INF不要开到0x3f3f3f3f(或者1e9),会WA,我改了下INF就过了。

完整代码:

#include <iostream>
#include <cstdio>
#include <cmath>
#include <string>
#include <cstring>
#include <algorithm>
#include <limits>
#include <vector>
#include <stack>
#include <queue>
#include <set>
#include <map>
#define lowbit(x) ( x&(-x) )
#define pi 3.141592653589793
#define e 2.718281828459045
using namespace std;
typedef long long ll;
const int maxN=1005;
const int INF=1e6+7;
//const int INF=0x3f3f3f3f;
int N, M, cnt, head[maxN];
int dp[maxN];
struct Eddge
{
    int to, nex, val;
    Eddge(int a=0, int b=-1, int c=0):to(a), nex(b), val(c) {}
}edge[maxN];
void addEddge(int u, int v, int val)
{
    edge[cnt]=Eddge(v, head[u], val);
    head[u]=cnt++;
}
void dfs(int u, int pre, int mid)
{
    if(head[u]==-1) { dp[u]=INF; return; }
    for(int tmp=head[u]; tmp!=-1; tmp=edge[tmp].nex)
    {
        int v=edge[tmp].to, val=edge[tmp].val;
        if(v==pre) continue;
        dfs(v, u, mid);
        dp[u]+=min(dp[v], val>mid?INF:val);
    }
}
bool check(int mid)
{
    for(int i=1; i<=N; i++) dp[i]=0;
    dfs(1, 0, mid);
    return dp[1]<=M?true:false;
}
int main()
{
    while(scanf("%d%d", &N, &M) && (N | M))
    {
        cnt=0;  memset(head, -1, sizeof(head));
        for(int i=1; i<N; i++)
        {
            int e1, e2, e3;
            scanf("%d%d%d", &e1, &e2, &e3);
            addEddge(e1, e2, e3);
        }
        int l=0, r=M, ans=-1;
        while(l<=r)
        {
            int mid=(l+r)>>1;
            if(check(mid)) { r=mid-1; ans=mid; }
            else l=mid+1;
        }
        printf("%d\n", ans);
    }
    return 0;
}

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

Wuliwuliii

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值