hdu 4274 Spy's Work 树形搜索

http://acm.hdu.edu.cn/showproblem.php?pid=4274

题意:

我们派出的间谍得到一些信息,信息包括N个职工分别负责N个部门,每个职工最多有一个上司,每个职工的工资最少为1,上司i负责部门i 而i的下属也属于部门i,给出m个部门的描述,

i < W 表示部门i的所有人的总工资小于w,(包括i以及i的下属,下边一样);

i > W 表示部门i的所有人的总工资大于W;

i = W 表示部门i所有人的总工资等于W

让你判断这些信息是否正确,如果寻在矛盾说明不正确。

思路:

比赛时,最后20分钟才有思路,不过没写完,。。郁闷。。

每个点low[i]记录i部门最少可得的工资(注意这里包括i的下属)heigh[i]记录可能的最大工资。

首先初始化low[i] = 1,heigh[i] = inf; 然后根据给出的m个信息更新 ,见代码说明,随后只要检查low[i] 是否小于等于heigh[i]就可以了。

PS;这里犯了一个超二逼的错误,在m个关系里输入了一个字符串直接取str[0]当a了,这样就只能去1到10的数了。。。检查了好久。。郁闷啊。。

View Code
#include <iostream>
#include <cstdio>
#include <cstring>
#include <algorithm>
#include <cmath>
#include <queue>
#include <stack>
#include <set>
#include <map>
#include <string>

#define CL(a,num) memset((a),(num),sizeof(a))
#define iabs(x)  ((x) > 0 ? (x) : -(x))
#define Min(a,b) (a) > (b)? (b):(a)
#define Max(a,b) (a) > (b)? (a):(b)

#define ll __int64

#define MOD 100000007
#define lc l,m,rt<<1
#define rc m + 1,r,rt<<1|1
#define pi acos(-1.0)
#define test puts("<------------------->")
#define maxn 100007
#define M 10017
#define N 10017
using namespace std;
//freopen("din.txt","r",stdin);

const ll inf = 100000007ll;
struct node{
    int v;
    int next;
}g[M];

int head[N],ct;
ll low[N],heigh[N];
int n,m;

void init(){
    ct = 0;
    CL(head,-1);
}

void add(int u,int v){
    g[ct].v = v;
    g[ct].next = head[u];
    head[u] = ct++;
}

void dfs(int pos){
    if (head[pos] == -1) return ;

    ll LOW = 0;
    for (int i = head[pos]; i != -1; i = g[i].next){
        int v = g[i].v;
        dfs(v);
        LOW += low[v];//只要记录最小的可能就好了,因为最大父亲可以取最大值
    }
    low[pos] = max(low[pos],LOW + 1);//注意加上本身的1
}

int main(){
   //freopen("din.txt","r",stdin);
    int i,x;
    while (~scanf("%d",&n)){
        init();//初始化

        low[1] = 1; heigh[1] = inf;
        for (i = 2; i <= n; ++i){
            scanf("%d",&x);
            add(x,i);
            low[i] = 1; heigh[i] = inf;
        }
        scanf("%d",&m);

        int x;
        ll y; char s[3];
        for (i = 0; i < m; ++i){
            scanf("%d%s%I64d",&x,s,&y);
            if (s[0] == '='){
                low[x] = Max(low[x],y);//等于时
                heigh[x] = Min(heigh[x],y);
            }
            else if (s[0] == '<'){//小于时
                heigh[x] = Min(heigh[x],y - 1);
            }
            else{//大于时
                low[x] = Max(low[x],y + 1);
            }
        }

        dfs(1);

        bool flag = false;
        for (i = 1; i <= n; ++i){
            if (low[i] > heigh[i]){
                flag = true;
                break;
            }
        }

        if (flag) printf("Lie\n");
        else printf("True\n");
    }
    return 0;
}

 

posted @ 2012-09-14 20:11  E_star  阅读(198)  评论(0编辑  收藏  举报