• 洛谷——P2417 课程


    P2417 课程

    裸地匈牙利算法,

    贪心的不断匹配,若没匹配,则匹配;反之,判断与之匹配的点能否在找另一个点匹配,若能,抢多这个点与之匹配

    时间复杂度$O(n imes m)$

    #include<iostream>
    #include<cstdio>
    #include<algorithm>
    #include<cstring>
    #define N 2000000
    using namespace std;
    
    struct node{
        int to,next;
    }e[N];
    int t,head[N],tot,p,n,match[N],dfn[N],ans;
    
    void add(int u,int v){
        e[++tot].to=v,e[tot].next=head[u],head[u]=tot;
    }
    
    bool dfs(int u,int t){
        for(int i=head[u];i;i=e[i].next){
            int v=e[i].to;
            if(dfn[v]!=t){
                dfn[v]=t;
                if(!match[v]||dfs(match[v],t)){
                    match[v]=u;return true;
                }
            }
        }
        return false;
    }
    
    int main()
    {
        scanf("%d",&t);
        while(t--){
            memset(head,0,sizeof(head));
            memset(match,0,sizeof(match));
            memset(dfn,0,sizeof(dfn));
            tot=ans=0;
            scanf("%d%d",&p,&n);
            for(int m,v,i=1;i<=p;i++){
                scanf("%d",&m);
                for(int j=1;j<=m;j++){
                    scanf("%d",&v),add(v,i);
                }
            }
            for(int i=1;i<=n;i++)
                if(dfs(i,i)) ++ans;
            if(ans>=p) printf("YES
    ");
            else printf("NO
    ");
        }
        
        return 0;
    }

    P2071 座位安排

    模板,又是模板,建图方式有一点儿不同,因为每一排有两个座位

    #include<iostream>
    #include<cstdio>
    #include<algorithm>
    #include<cstring>
    #define N 2000000
    using namespace std;
    
    struct node {
        int to,next;
    } e[N];
    int t,head[N],tot,p,n,match[N],dfn[N],ans;
    
    void add(int u,int v) {
        e[++tot].to=v,e[tot].next=head[u],head[u]=tot;
    }
    
    bool dfs(int u,int t) {
        for(int i=head[u]; i; i=e[i].next) {
            int v=e[i].to;
            if(dfn[v]!=t) {
                dfn[v]=t;
                if(!match[v]||dfs(match[v],t)) {
                    match[v]=u;
                    return true;
                }
            }
        }
        return false;
    }
    
    int main() {
        memset(head,0,sizeof(head));
        memset(match,0,sizeof(match));
        memset(dfn,0,sizeof(dfn));
        tot=ans=0;
        scanf("%d",&n);
        for(int x,y,i=1; i<=n*2; i++) {
            scanf("%d%d",&x,&y);
            add(i,x),add(i,x+n),add(i,y),add(i,y+n);
        }
        for(int i=1; i<=n*2; i++)
            if(dfs(i,i)) ++ans;
        printf("%d
    ",ans);
    
        return 0;
    }

    P1894 [USACO4.2]完美的牛栏The Perfect Stall

    裸题

    #include<iostream>
    #include<cstdio>
    #include<algorithm>
    #include<cstring>
    #define N 2000000
    using namespace std;
    
    struct node {
        int to,next;
    } e[N];
    int t,head[N],tot,m,n,match[N],dfn[N],ans;
    
    void add(int u,int v) {
        e[++tot].to=v,e[tot].next=head[u],head[u]=tot;
    }
    
    bool dfs(int u,int t) {
        for(int i=head[u]; i; i=e[i].next) {
            int v=e[i].to;
            if(dfn[v]!=t) {
                dfn[v]=t;
                if(!match[v]||dfs(match[v],t)) {
                    match[v]=u;
                    return true;
                }
            }
        }
        return false;
    }
    
    int main() {
        memset(head,0,sizeof(head));
        memset(match,0,sizeof(match));
        memset(dfn,0,sizeof(dfn));
        tot=ans=0;
        scanf("%d%d",&n,&m);
        for(int v,x,i=1; i<=n; i++) {
            scanf("%d",&x);
            for(int j=1;j<=x;j++) {
                scanf("%d",&v);
                add(i,v);
            }
        }
        for(int i=1; i<=n; i++)
            if(dfs(i,i)) ++ans;
        printf("%d
    ",ans);
    
        return 0;
    }
  • 相关阅读:
    杨辉三角
    数组的两种输出方法
    整数分割各位数
    Fibonacci
    imageview圆角的实现
    listview定位到上次显示的位置
    安卓客户端 扫描二维码登陆
    java,UDP协议简单实现
    java 反射机制的实例
    js中正则表达式 书写方法
  • 原文地址:https://www.cnblogs.com/song-/p/9806853.html
Copyright © 2020-2023  润新知