ZOJ-3601-Unrequited Love【9th浙江省赛】【模拟】【STL】

ZOJ-3601-Unrequited Love

                    Time Limit: 16 Seconds      Memory Limit: 131072 KB

There are n single boys and m single girls. Each of them may love none, one or several of other people unrequitedly and one-sidedly. For the coming q days, each night some of them will come together to hold a single party. In the party, if someone loves all the others, but is not loved by anyone, then he/she is called king/queen of unrequited love.

Input

There are multiple test cases. The first line of the input is an integer T ≈ 50 indicating the number of test cases.

Each test case starts with three positive integers no more than 30000 – n m q. Then each of the next n lines describes a boy, and each of the next m lines describes a girl. Each line consists of the name, the number of unrequitedly loved people, and the list of these people’s names. Each of the last q lines describes a single party. It consists of the number of people who attend this party and their names. All people have different names whose lengths are no more than 20. But there are no restrictions that all of them are heterosexuals.

Output

For each query, print the number of kings/queens of unrequited love, followed by their names in lexicographical order, separated by a space. Print an empty line after each test case. See sample for more details.

Sample Input
2
2 1 4
BoyA 1 GirlC
BoyB 1 GirlC
GirlC 1 BoyA
2 BoyA BoyB
2 BoyA GirlC
2 BoyB GirlC
3 BoyA BoyB GirlC
2 2 2
H 2 O S
He 0
O 1 H
S 1 H
3 H O S
4 H He O S

Sample Output
0
0
1 BoyB
0

0
0

题目链接:ZOJ-3601

题目大意:输入n个男(女)生以及他们分别喜欢的女(男)生名字,然后找出一个人,他喜欢party上的所有人但没有一个人喜欢他(2333是挺惨的)

题目思路:直接模拟,但是考到一点逻辑问题。比如可以得到, 如果存在这么一个人,那只可能存在一个。

对于我来说,这道题的数据的处理存储以及逻辑分析是一个难点。

eg:处理的时候,eg : a b c d e f

a喜欢b,b不喜欢a;a喜欢c,c也喜欢a —–>a是不满足条件的

然后我们直接看c。跳过b的原因是:b不喜欢a,所以已经不符合条件了

假设c和d e f之间的关系都满足条件,但是我们不能忘记考虑c 和a b的关系,所以需要另外处理。

      ①如果c和a,b满足条件,那么c就是答案.
      ②如果不满足条件,那么就不存在答案 : d e f满足了c,即他们本身就不符合条件了(因为他们都被c喜欢)

以下是代码:

#include <bits/stdc++.h>
#define mst(a) memset(a,0,sizeof (a))
#define FOR(i,n) for (int i = 0; i < n; i++)
#define INF 1e9
#define eps 1e-10
using namespace std;

typedef long long ll;
set <int> se[30005];
map <string,int> mp;
string p[30005];
int cnt = 0;
int getID(string s)
{
    if(mp[s]) return mp[s];
    else
    {
        mp[s] = ++cnt;
        return mp[s];
    } 
}
int main(){
    int t;
    cin >> t;
    while(t--)
    {
        cnt = 0;  //初始化编号 
        for (int i = 0; i < 30001; i++) p[i].clear();
        mp.clear();
        for (int i = 0; i < 30001; i++) se[i].clear();
        int n,m,q;
        cin >> n >> m >> q;
        string s,ret;
        int num;
        for (int i = 0; i < n + m; i++)  //输入 
        {
            cin >> s >> num;
            int s_id = getID(s); 
            for (int j = 0; j < num; j++)
            {
                cin >> ret;
                se[s_id].insert(getID(ret));
            }
        }       
        while(q--)
        {
            int k;
            cin >> k;
            for (int i = 0; i < k; i++)
            {
                cin >> ret;
                p[i] = ret;
            }
            int pos = 0;
            string ans = p[0];
            for (int i = 0; i < k; i++)
            {
                if (!se[getID(p[pos])].count(getID(p[i])) || se[getID(p[i])].count(getID(p[pos]))) //如果他不爱某个人,或者某个人爱他,说明这个人不符合条件
                {
                    pos = i;  //说明i之前的都不符合条件
                    ans = p[i];
                }
            }
            for (int i = 0; i < pos; i++)  //检查 pos之前的是否满足条件 
            {
                if (!se[getID(p[pos])].count(getID(p[i])) || se[getID(p[i])].count(getID(p[pos])))
                {
                    ans = "";
                    break;
                }
            }
            if (ans == "") cout << 0 << endl;
            else cout << 1 << " " << ans << endl;  //如果存在只可能存在一个 
        }
        cout << endl;
    } 
    return 0;
}

你可能感兴趣的:(ZOJ,3601)