codeforces1027F. Session in BSU

题目链接

codeforces1027F. Session in BSU

题解

二分图匹配就fst了....显然是过去的,不过tle test87估计也pp了,好坑
那么对于上面做匹配的这个二分图分情况讨论一下
考虑当前的联通块:
边数大于点数:这样肯定是无解的
边数 = 点数:这是一棵基环树,每个日期都会被用,输出最大值
边数 < 点数:这是一棵树,输出次大值
并查集维护一下联通块

代码

#include<cstdio> 
#include<cstring> 
#include<algorithm> 
inline int read() { 
    int x = 0,f = 1; 
    char c = getchar(); 
    while(c < '0' || c > '9'){if(c == '-')f = -1; c = getchar(); } 
    while(c <= '9' && c >= '0') x = x * 10 + c - '0',c = getchar(); 
    return x *f ; 
} 
const int maxn = 2000007; 
int a[maxn],b[maxn],ha[maxn << 1];  int n; 

/*struct node { 
    int v,next;
}edge[maxn << 1]; 
int head[maxn << 1],num = 0; 
inline void add_edge(int u,int v) { 
    edge[++ num].v = v; edge[num].next = head[u];head[u] = num; 
} 
int link[maxn << 1],vis[maxn << 1]; 
bool match(int x,int fa) { 
    for(int i = head[x];i;i = edge[i].next) { 
        int v = edge[i].v; 
        if(vis[v] != fa) { 
            vis[v] = fa; 
            if(!link[v] || match(link[v],fa)) { 
                link[v] = x; 
                return true; 
            } 
        } 
            
    } 
    return false; 
} */ 
int fa[maxn << 1];  
int mx[maxn << 1],mx2[maxn << 1]; 
int tag[maxn << 1]; 
inline int find(int x) { 
    if(fa[x] != x) fa[x] = find(fa[x]); 
    return fa[x]; 
} 
int main()  { 
    n = read(); 
    int num = 0; 
    for(int i = 1;i <= n;++ i) { 
        a[i] = read();b[i] = read(); 
        ha[++ num] = a[i],ha[++ num] = b[i]; 
    } 
    std::sort(ha + 1,ha + num + 1); 
    int len = std::unique(ha + 1,ha + num + 1) - ha - 1; 
    for(int i = 1;i <= n;++ i) { 
        a[i] = std::lower_bound(ha + 1,ha + len + 1,a[i]) - ha; 
        b[i] = std::lower_bound(ha + 1,ha + len + 1,b[i]) - ha; 
    } 
    for(int i = 1;i <= len;++ i) fa[i] = i, mx[i] = i;
    for(int i = 1;i <= n;++ i) { 
        int x = find(a[i]),y = find(b[i]); 
        if(x != y) {
            fa[y] = x; 
            if(tag[y]) tag[x] = 1; 
            if(mx[y] > mx[x]) mx2[x] = std::max(mx2[x],std::max(mx2[y], mx[x])),mx[x] = mx[y]; 
            else mx2[x] = std::max(mx2[x],mx[y]); 
        } 
        else if(!tag[x]) tag[x] = 1; 
        else { 
            puts("-1") ; 
            return 0; 
        }   
    } 
    int ans = 0;  
    for(int i = 1; i <= len; i++) {
        int k = find(i); 
        if(tag[k]) ans = std::max(ans,ha[mx[k]]);
        else ans = std::max(ans,ha[mx2[k]]);
    } 
    printf("%d\n",ans); 
    return 0; 
} 

猜你喜欢

转载自www.cnblogs.com/sssy/p/9649179.html