HDU 5961 传递 题解

题目

我们称一个有向图G是 传递的,当且仅当对任意三个不同的顶点a,,若G中有 一条边从a到b且有一条边从b到c ,则G中同样有一条边从a到c。
我们称图G是一个 竞赛图,当且仅当它是一个有向图且它的基图是完全图。换句 话说,将完全图每条边定向将得到一个竞赛图。
下图展示的是一个有4个顶点的竞赛图。

现在,给你两个有向图\(P=(V,E_p)\)\(Q = (V,E_e)\),满足:

  1. \(E_P\)与E_$e没有公共边;
  2. \((V,E_p \cup E+e)\)是一个竞赛图。
    你的任务是:判定是否\(P,Q\)同时为传递的。

输入格式

包含至多20组测试数据。
第一行有一个正整数,表示数据的组数。
对于每组数据,第一行有一个正整数n。接下来n行,每行为连续的n个字符,每 个字符只可能是’-’,’P’,’Q’中的一种。

  • 如果第i行的第j个字符为’P’,表示有向图P中有一条边从i到j;
  • 如果第i行的第j个字符为’Q’,表示有向图Q中有一条边从i到j;
  • 否则表示两个图中均没有边从i到j。
    保证\(1 <= n <= 2016\),一个测试点中的多组数据中的n的和不超过16000。保证输入的图一定满足给出的限制条件。

输出格式

对每个数据,你需要输出一行。如果P! Q都是传递的,那么请输出’T’。否则, 请输出’N’ (均不包括引号)。

输入样例

4
4
-PPP
--PQ
---Q
----
4
-P-P
--PQ
P--Q
----
4
-PPP
--QQ
----
--Q-
4
-PPP
--PQ
----
--Q-

输出样例

T
N
T
N

题解

样例图

注:在样例2中,P不是传递的。在样例4中,Q不是传递的。

假设\(1->2,2->3\)有边, 但\(1->3\)无边, 就不是传递的, 那么什么情况下\(1->3\)无边呢, 一种情况是\(3->1\)有边, 另一种情况是另一个图在\(1,3\)之间有边

第一种情况, \(1->2,2->3,3->1\), 这显然是一个环

第二种情况, 当另一张图有\(3->1\), 拼起来就构成一个环;当另一张图有\(1->3\), 每条边反向拼起来也是一个环

所以使用拓扑排序找环即可。

代码

#include <cstdio>
#include <cstring>
#include <queue>
#include <vector>
std::vector<int> edge[2017];
std::queue<int> Q;
int m, n, in[2017], cnt, newn;
int main() {
    scanf("%d", &n);
    while (n--) {
        scanf("%d", &m);
        memset(in, 0, sizeof(in));
        for (int i = 1; i <= m; i++) edge[i].clear();
        while (!Q.empty()) Q.pop();
        for (int i = 1; i <= m; ++i)
            for (int j = 1; j <= m; ++j) {
                char ch;
                scanf(" %c", &ch);
                if (ch == 'P') in[j]++, edge[i].push_back(j);
                else if (ch == 'Q') in[i]++, edge[j].push_back(i);
            }
        for (int i = 1; i <= m; i++) if (!in[i]) Q.push(i);
        cnt = 0;
        while (!Q.empty()) {
            newn = Q.front(), Q.pop(), cnt++;
            for (int i = 0; i < edge[newn].size(); i++) {
                in[edge[newn][i]]--;
                if (in[edge[newn][i]] == 0) Q.push(edge[newn][i]);
            }
        }
        puts((cnt == m)?"T":"N");
    }
}
posted @ 2020-05-20 16:37  YouXam  阅读(168)  评论(0编辑  收藏  举报