关押罪犯

 

传送门:https://www.luogu.org/problemnew/show/P1525

要使怨气值最小,不妨按怨气值从大到小排序,使怨气值越大的两个人越尽可能的分开。

但是假若1&2互为敌人,3&4互为敌人,是把1、3关在一起,还是1、4关在一起呢,这得取决于下面的数据。

但现在是不知道将来的情况如何,因此采用“敌人的敌人是朋友”这一策略。先把两个人的关系定义为敌人,假定1&2为敌人,3&4为敌人,这时1&3也为敌人,则2&3是朋友,将它们关进一个监狱,若遇到两个人已经在同一监狱了,因为怨气值是从大到小的,则这两个人之间的怨气值就是最大怨气值。

代码

#include<cstdio>
#include<algorithm> 
using namespace std;
const int N = 20010;
int n,m,fa[N],dr[N];
struct node
{
    int a,b,c;
}t[100010];
bool cmp(node x,node y){return x.c > y.c;}
int find(int x)
{
    if(x != fa[x]) fa[x] = find(fa[x]);
    return fa[x];
 } 
bool pd(int x,int y)
{
    x = find(x);
    y = find(y);
    if(x == y) return true;
    else return false;
}
int main()
{
    scanf("%d%d",&n,&m);
    for(int i = 1;i <= n;i++) fa[i] = i; 
    for(int i = 1;i <= m;i++)
        scanf("%d%d%d",&t[i].a,&t[i].b,&t[i].c);
    sort(t+1,t+m+1,cmp);
    for(int i = 1;i <= m;i++)
    {
        if(find(t[i].a) == find(t[i].b))//两人被关在了同一监狱
        {
            printf("%d",t[i].c);
            return 0;
        }
        else//两人没被关在同一监狱 
        {
            if(dr[t[i].a] == 0)//a还没有敌人 
                dr[t[i].a] = t[i].b;//它俩互为敌人 
            else//a有敌人了 
                fa[find(dr[t[i].a])] = find(t[i].b);//敌人的敌人是朋友 
            if(dr[t[i].b] == 0) 
                dr[t[i].b] = t[i].a;
            else
                fa[find(dr[t[i].b])] = find(t[i].a);
        }
    }
    printf("0");
    return 0;
}

 

posted @ 2018-10-24 15:06  我的露娜不会飘  阅读(122)  评论(0编辑  收藏  举报