noip2010(关押罪犯)

4844: Noip2010 关押罪犯

Time Limit: 4 Sec  Memory Limit: 128 MB
Submit: 18  Solved: 12
[Submit][Status][Web Board]

Description

S城现有两座监狱,一共关押着 N名罪犯,编号分别为 1~N。他们之间的关系自然也极不和谐。很多罪犯之间甚至

积怨已久,如果客观条件具备则随时可能爆发冲突。我们用“怨气值” (一个正整数值)来表示某两名罪犯之间

的仇恨程度,怨气值越大,则这两名罪犯之间的积怨越多。如果两名怨气值为 c 的罪犯被关押在同一监狱,他们

俩之间会发生摩擦,并造成影响力为 c 的冲突事件。每年年末,警察局会将本年内监狱中的所有冲突事件按影响

力从大到小排成一个列表,然后上报到 S 城 Z 市长那里。公务繁忙的 Z 市长只会去看列表中的第一个事件的影

响力,如果影响很坏,他就会考虑撤换警察局长。在详细考察了 N 名罪犯间的矛盾关系后,警察局长觉得压力巨

大。他准备将罪犯们在两座监狱内重新分配,以求产生的冲突事件影响力都较小,从而保住自己的乌纱帽。假设只

要处于同一监狱内的某两个罪犯间有仇恨,那么他们一定会在每年的某个时候发生摩擦。那么,应如何分配罪犯,

才能使 Z 市长看到的那个冲突事件的影响力最小?这个最小值是多少?

Input

输入文件的每行中两个数之间用一个空格隔开。

第一行为两个正整数 N和 M,分别表示罪犯的数目以及存在仇恨的罪犯对数。

接下来的 M行每行为三个正整数 aj,bj,cj,表示 aj号和 bj号罪犯之间存在仇恨,其怨

气值为 cj。数据保证 N b a j j

≤ < ≤ 1 , 000 , 000 , 000 , 1 0 ≤ < j

c ,且每对罪犯组合只出现一次。

n<=20000, m<=100000

Output

共1 行,为 Z 市长看到的那个冲突事件的影响力。如果本年内监狱

中未发生任何冲突事件,请输出 0。

Sample Input

4 6
1 4 2534
2 3 3512
1 2 28351
1 3 6618
2 4 1805
3 4 12884 

Sample Output

3512

HINT

按怨气值从小到大排序,那么找到的第一个发生冲突的即为最大值,

建一个2n大的并查集,一个为a监狱一个为b监狱,

不断把x,y,放到不同的监狱中去,直到出现矛盾为止

#include<cstdio>
#include<algorithm>
using namespace std;

struct my{
    int a,b,c;
};

const int maxn=100000+10;
my zui[maxn];
int fa[maxn];

bool cmp(const my x,const my y){
     return x.c>y.c;
}

int getfa(int x){
    if(x==fa[x]) return fa[x];
    return fa[x]=getfa(fa[x]);
}

int main(){
    int n,m;
    scanf("%d%d",&n,&m);
    for (int i=1;i<=n*2;i++) fa[i]=i;
    for (int i=1;i<=m;i++) scanf("%d%d%d",&zui[i].a,&zui[i].b,&zui[i].c);
    sort(zui+1,zui+1+m,cmp);
    for(int i=1;i<=m;i++){
        int x=getfa(zui[i].a);
        int y=getfa(zui[i].b);
        if(x==y){
            printf("%d\n",zui[i].c);
            return 0;
        }
        fa[y]=getfa(zui[i].a+n);
        fa[x]=getfa(zui[i].b+n);
    }
    printf("0\n");
return 0;
}

原文地址:https://www.cnblogs.com/lmjer/p/9204710.html

时间: 2024-10-11 22:58:55

noip2010(关押罪犯)的相关文章

noip2010 关押罪犯

题目描述 Description S 城现有两座监狱,一共关押着N 名罪犯,编号分别为1~N.他们之间的关系自然也极 不和谐.很多罪犯之间甚至积怨已久,如果客观条件具备则随时可能爆发冲突.我们用"怨 气值"(一个正整数值)来表示某两名罪犯之间的仇恨程度,怨气值越大,则这两名罪犯之 间的积怨越多.如果两名怨气值为c 的罪犯被关押在同一监狱,他们俩之间会发生摩擦,并 造成影响力为c 的冲突事件. 每年年末,警察局会将本年内监狱中的所有冲突事件按影响力从大到小排成一个列表, 然后上报到S 城

NOIP2010关押罪犯[并查集|二分答案+二分图]

题目描述 S 城现有两座监狱,一共关押着N 名罪犯,编号分别为1~N.他们之间的关系自然也极不和谐.很多罪犯之间甚至积怨已久,如果客观条件具备则随时可能爆发冲突.我们用“怨气值”(一个正整数值)来表示某两名罪犯之间的仇恨程度,怨气值越大,则这两名罪犯之间的积怨越多.如果两名怨气值为c 的罪犯被关押在同一监狱,他们俩之间会发生摩擦,并造成影响力为c 的冲突事件. 每年年末,警察局会将本年内监狱中的所有冲突事件按影响力从大到小排成一个列表,然后上报到S 城Z 市长那里.公务繁忙的Z 市长只会去看列表

回档|NOIP2010 关押罪犯

描述 S城现有两座监狱,一共关押着N名罪犯,编号分别为1~N.他们之间的关系自然也极不和谐.很多罪犯之间甚至积怨已久,如果客观条件具备则随时可能爆发冲 突.我们用“怨气值”(一个正整数值)来表示某两名罪犯之间的仇恨程度,怨气值越大,则这两名罪犯之间的积怨越多.如果两名怨气值为c的罪犯被关押在同一 监狱,他们俩之间会发生摩擦,并造成影响力为c的冲突事件.每年年末,警察局会将本年内监狱中的所有冲突事件按影响力从大到小排成一个列表,然后上报到S 城Z市长那里.公务繁忙的Z市长只会去看列表中的第一个事件

NOIP2010 关押罪犯(图论+二分)

考试的时候写的最大生成树,然后二分图染色,因为这样两个矛盾很大的罪犯不会被分在一个监狱里面. 然而最大生成树超时,80分. 正解为二分边权,将边权值大于mid的全部连边构图,判断是否为二分图,如果不是二分图,那么无解. 如果无解,则说明边权的限制条件太小了,因为连的边太多,不容易形成二分图:如果有解,则说明边权的限制条件太大,因为更少的边有利于形成二分图. 80分代码,最大生成树: #include<cstdio> #include<cstring> #include<alg

noip2010关押罪犯

题目链接:传送门 题目思路:并查集高级应用(类似食物链那道题),主要是维护两个集合(监狱里犯人的关系),同一个集合里的是朋友,否则是敌人,如果敌人在同一间监狱里, 则最小的最大冲突值求出. #include <iostream> #include <cstdio> #include <cstdlib> #include <cmath> #include <algorithm> #include <cstring> #include &

NOIP2010关押罪犯 二分+二染色

这个题一上来 没有思路,后来想没有思路就二分吧 那么我们来二分 首先,大于当前的mid值的关系,不能出现在一个集合里 (即关系形成的图是一个二分图,判定二分图可以二染色) 如果不能形成二分图,那么说明有些关系要在一个集合里,那就向上二分 否则向下二分 #include<cstdio> #include<cstring> #include<queue> #include<set> #include<cstdlib> #include<algo

[noip2010]关押罪犯 并查集

第一次看的时候想到了并查集,但是不知道怎么实现: 标解,f[i]表示i所属的集合,用f[i+n]表示i所属集合的补集,实现的很巧妙,可以当成一个使用并查集的范例: 1 #include<iostream> 2 #include<cstdio> 3 #include<cstring> 4 #include<cstdlib> 5 #include<map> 6 #include<ctime> 7 #include<vector>

[NOIP2010]关押罪犯(二分+二分图染色)

传送门 大意:我们把图分为两部分,使得两部分中的内部边的最大权值最小. 思路:哎,拿到题的时候想了二分图染色,发现不好做,但我没有想到二分,只好最后去骗了一个30分.正确的思路是:首先我们要 去二分最大的冲突边的是哪一条(按照权值二分),因为当二分的边权增大时,连的边也就越少,连通块的数目就越多,冲突就越少,所以边权是可以二分的,在二分过后用二分图判定,如果可以染成二分图即为可行的解. 代码: #include<cstdio> #include<algorithm> #includ

NOIP2010 关押罪犯 (并查集)

若x,y有关系 将x与y的补集, y与x的补集建立关系 const maxn=20008; maxm=100008; var eg:array[0..maxm,1..3] of longint; f:array[0..maxn*2] of longint; i,j,m,n,x,y,z:longint; procedure swap(var a,b:longint); var c:longint; begin c:=a;a:=b;b:=c; end; function find(x:longint