HDU1512

额  并查集 用启发式搜索

但是维护里面最大值时是要用优先队列的 一开始傻傻的以为用一个4个位置的数组就够了 觉得第一大的决斗完后后要么第一要么第二 真tm是智障。。。

额。。。依稀记得新生赛初赛的时候犯过差不多的智商错误 那时也是应该用优先队列的 

象征性贴个代码:

#include <cstdio>
#include <iostream>
#include <cstring>
#include <algorithm>
#include <cmath>
#include <queue>
#include <stack>
#include <bitset>
#include <vector>
#pragma comment(linker, "/STACK:1024000000,1024000000")
#define inf -(0x7fffffff);
using namespace std;
const int maxn=100005;
priority_queue<int>qu[maxn];
int a[maxn],order[10],m,n;
int mx1[maxn],mx2[maxn],f[maxn],h[maxn];
int find(int x)
{
    if(f[x]!=x) f[x]=find(f[x]);
    return f[x];
}
/*void arrange(int x,int y,int p,int q)
{
    memset(order,0,sizeof(order));
    mx1[q]/=2;
    mx1[p]/=2;
    order[1]=mx1[q];
    order[2]=mx1[p];
    order[3]=mx2[q];
    order[4]=mx2[p];
    sort(order+1,order+1+4);
}*/
int qfsunion(int x,int y)
{
    x=find(x),y=find(y);
    if(x==y) return -1;
    int sx=qu[x].top();
    qu[x].pop();
    sx/=2;
    int sy=qu[y].top();
    qu[y].pop();
    sy/=2;
    if(qu[x].size()>qu[y].size()) swap(x,y);
    f[x]=y;
    while(!qu[x].empty())
    {
        int nn=qu[x].top();
        qu[x].pop();
        qu[y].push(nn);
    }
    qu[y].push(sx);
    qu[y].push(sy);
    return qu[y].top();

}
int main()
{
    while(scanf("%d",&n)!=EOF)
    {
        for(int i=1;i<=n;i++)
        while(!qu[i].empty()) qu[i].pop();
        memset(a,0,sizeof(a));
        memset(h,0,sizeof(h));
        for(int i=1; i<=n; i++)
        {
            scanf("%d",&a[i]);
            f[i]=i;
            qu[i].push(a[i]);
            //mx1[i]=a[i];
            //mx2[i]=inf;
        }
        scanf("%d",&m);
        while(m--)
        {
            int x,y;
            scanf("%d%d",&x,&y);
            printf("%d\n",qfsunion(x,y));
        }
    }
    return 0;
}
/*
7
1 5 37 3 4 2 5
5
1 3
18
2 5
2
3 4
9
2 7
2
6 7
2
*/

猜你喜欢

转载自blog.csdn.net/weixin_39302444/article/details/79601677