标题链接

标题描述

布置宴席最奇妙的事情,就是给前来参宴的各位来宾组织座位。无论如何,总不能把两个死对头排到同一张宴会桌旁!这个艰巨任务现在就交给你,对任何一对客人,请编写程序告知主人他们是否能被组织同席

输入格局:

输入榜首行给出3个正整数:N(≤100),即前来参宴的来宾总人数,则这些人从1N编号;M为已知两两来宾之间的联系数;K为查询的条数。随后M行,每行给出一对来宾之间的联系,格局为:来宾1 来宾2 联系,其中联系为1表明是朋友,-1表明是死对头。注意两个人不可能既是朋友又是敌人。最终K行,每行给出一对需要查询的来宾编号。这里假定朋友的朋友也是朋友。但敌人的敌人并不一定就是朋友,朋友的敌人也不一定是敌人。只要单纯直接的仇视联系才是肯定不能同席的。

输出格局:

对每个查询输出一行结果:假如两位来宾之间是朋友,且没有仇视联系,则输出No problem;假如他们之间并不是朋友,但也不仇视,则输出OK;假如他们之间有仇视,然而也有一起的朋友,则输出OK but...;假如他们之间只要仇视联系,则输出No way

输入样例:

7 8 4
5 6 1
2 7 -1
1 3 1
3 4 1
6 7 -1
1 2 1
1 4 1
2 3 -1
3 4
5 7
2 3
7 2

输出样例:

No problem
OK
OK but...
No way

解题思路

首先,标题很长,咱们看过标题后一定要搞清楚要干什么,理清思路,再将代码实现。我做这道题是,没有看完整标题的意思,就去做了,结果输出时遇到问题,又补救代码,浪费时间。

给定N个人,再给出M个两两联系,咱们可以用一个二维数组p来记录每两个人之间的联系,默以为0。最主要的部分就是这句话这里假定朋友的朋友也是朋友。但敌人的敌人并不一定就是朋友,朋友的敌人也不一定是敌人。只要单纯直接的仇视联系才是肯定不能同席的。最终输出时也要求咱们要判别是否有一起的朋友,所以就用到了并查集常识。最终就是处理输入输出的问题。

并查集 (对调集进行兼并和查询)

int f[1000];//x的父结点
int find(int x)//找祖先结点 
{ 
    if (f[x] != x) f[x] = find(f[x]); 
    return f[x]; 
}
//初始时,每个结点祖先结点初始化为自己
for (int i = 1; i <= n; i++) f[i] = i;
//兼并调集     假如两人之间是朋友则将两人树立联系。
if (c==1 && f[a] != f[b]) f[find(a)] = find(b);
//查询  两人之间仇视,有公共朋友则输出榜首句,没有公共朋友输出第二句。
if (p[a][b] == -1 && find(a) == find(b)) cout << "OK but..."<<endl; 
else if(p[a][b] == -1 && find(a) != find(b)) cout << "No way" << endl;

AC代码

#include<iostream>
#include<algorithm>
#include<string>
using namespace std;
typedef long long ll;
int p[1000][1000] = {0};
int f[1000];//x的父结点
int find(int x)//找祖先结点
{
    if (f[x] != x) f[x] = find(f[x]);
    return f[x];
}
int main()
{
    int n,m,k;
    cin >> n >> m >> k;
    //每个结点祖先结点初始化为自己
    for (int i = 1; i <= n; i++) f[i] = i;
    while (m--)
    {
        int a, b, c;
        cin >> a >> b >> c;
        p[a][b] = p[b][a] = c;
        //兼并调集
        if (c==1 && f[a] != f[b]) f[find(a)] = find(b);
    }
    while (k--)
    {
        int a, b;
        cin >> a >> b;
        if (p[a][b] == 1) cout << "No problem" << endl;
        else if (p[a][b] == 0) cout << "OK" << endl;
        else if (p[a][b] == -1 && find(a) == find(b)) cout << "OK but..."<<endl;
        else if(p[a][b] == -1 && find(a) != find(b)) cout << "No way" << endl;
    }
    return 0;
}