zoukankan      html  css  js  c++  java
  • POJ 1904 King's Quest(强连通图)题解

    题意:n个王子有自己喜欢的ki个公主,有n个公主,每个王子只能娶一个自己喜欢的公主且不能绿别的王子。现在给你一种王子娶公主的方案,并且保证这种方案是正确的。请你给出,每个王子能娶哪些公主,要求娶这些公主时,其他王子也能娶到公主。

    思路:还以为是完全匹配,直接暴力匹配显然TLE了。正解是缩点...我们把每个王子指向自己喜欢的公主们,然后把给定的方案中的公主指向自己嫁给的王子,然后缩点,同一个点中王子喜欢的公主都能娶。因为每个王子指向的肯定都是公主(至少两个),公主指向的肯定都是王子,所以想要形成一个强连通图这个图中王子公主数量肯定是相同的,那么假如王子选择一个自己喜欢的公主,那么这个图中的其他的王子可以选择其他的公主,显然肯定能完全匹配。

    代码:

    #include<set>
    #include<map>
    #include<stack>
    #include<cmath>
    #include<queue>
    #include<vector>
    #include<string>
    #include<cstdio>
    #include<cstring>
    #include<sstream>
    #include<iostream>
    #include<algorithm>
    typedef long long ll;
    using namespace std;
    const int maxn = 4000 + 10;
    const int MOD = 1e9 + 7;
    const int INF = 0x3f3f3f3f;
    int head[maxn], ans[maxn], tot;
    struct Edge{
        int to, next;
    }edge[maxn * maxn];
    int low[maxn], dfn[maxn], Stack[maxn], belong[maxn];
    int index, top, scc;
    bool instack[maxn];
    void addEdge(int u, int v){
        edge[tot].to = v;
        edge[tot].next = head[u];
        head[u] = tot++;
    }
    void tarjan(int u){
        int v;
        low[u] = dfn[u] = ++index;
        Stack[top++] = u;
        instack[u] = true;
        for(int i = head[u]; i != -1; i = edge[i].next){
            v = edge[i].to;
            if(!dfn[v]){
                tarjan(v);
                if(low[u] > low[v]) low[u] = low[v];
            }
            else if(instack[v] && low[u] > dfn[v]){
                low[u] = dfn[v];
            }
        }
        if(low[u] == dfn[u]){
            scc++;
            do{
                v = Stack[--top];
                instack[v] = false;
                belong[v] = scc;
            }while(v != u);
        }
    }
    void solve(int n){
        memset(dfn, 0, sizeof(dfn));
        memset(instack, false, sizeof(instack));
        index = scc = top = 0;
        for(int i = 1; i <= n; i++){
            if(!dfn[i])
                tarjan(i);
        }
    }
    void init(){
        tot = 0;
        memset(head, -1, sizeof(head));
    }
    int main(){
        int n;
        while(~scanf("%d", &n)){
            int k, tmp;
            init();
            for(int i = 1; i <= n; i++){
                scanf("%d", &k);
                while(k--){
                    scanf("%d", &tmp);
                    addEdge(i, tmp + n);
                }
            }
            for(int i = 1; i <= n; i++){
                scanf("%d", &tmp);
                addEdge(tmp + n, i);
            }
            solve(2 * n);
            int ret;
            for(int u = 1; u <= n; u++){
                ret = 0;
                for(int i = head[u]; i != -1; i = edge[i].next){
                    int v = edge[i].to;
                    if(belong[v] == belong[u]){
                        ans[ret++] = v - n;
                    }
                }
                sort(ans, ans + ret);
                printf("%d", ret);
                for(int i = 0; i < ret; i++){
                    printf(" %d", ans[i]);
                }
                printf("
    ");
            }
        }
        return 0;
    }
  • 相关阅读:
    frame和iframe区别
    idea基本
    Spring中加载xml配置文件的六种方式
    java中Map,List与Set的区别
    java集合框架
    springmvc IDEA
    springmvc 精华
    eclipse 中 git 解决冲突(重点)
    启动Tomcat报错 java.util.zip.ZipException: invalid LOC header (bad signature)
    PowerDesigner 提示 Existence of index、key、reference错误
  • 原文地址:https://www.cnblogs.com/KirinSB/p/10464958.html
Copyright © 2011-2022 走看看