2017年11月23日 星期四

(BZOJ) 4337: BJOI2015 树的同构

http://www.lydsy.com/JudgeOnline/problem.php?id=4337

#include <iostream>
#include <cstdio>
#include <vector>
#include <algorithm>
#include <cstring>
#include <utility>
#include <cmath>
#include <ctime>
#include <cstdlib>
#include <queue>
#include <stack>
#include <map>
using namespace std;

#define LL   long long
#define ld   long double
#define pii  pair<int,int>
#define pLL  pair<LL,LL>
#define vint vector<int>
#define vLL  vector<LL>

#define SZ(x) ((int)(x).size())
#define ALL(x) (x).begin(),(x).end()
#define F first
#define S second
#define MP make_pair
#define PB push_back

#define Si(x) scanf("%d",&(x));
#define Sii(x,y) scanf("%d %d",&(x),&(y));
#define Siii(x,y,z) scanf("%d %d %d",&(x),&(y),&(z));
#define Siiii(x,y,z,w) scanf("%d %d %d %d",&(x),&(y),&(z),&(w));
#define Siiiii(x,y,z,w,a) scanf("%d %d %d %d %d",&(x),&(y),&(z),&(w),&(a));
#define Siiiiii(x,y,z,w,a,b) scanf("%d %d %d %d %d %d",&(x),&(y),&(z),&(w),&(a),&(b));
#define SL(x) scanf("%lld",&(x));
#define SLL(x,y) scanf("%lld %lld",&(x),&(y));
#define SLLL(x,y,z) scanf("%lld %lld %lld",&(x),&(y),&(z));
#define SLLLL(x,y,z,w) scanf("%lld %lld %lld %lld",&(x),&(y),&(z),&(w));
#define SLLLLL(x,y,z,w,a) scanf("%lld %lld %lld %lld %lld",&(x),&(y),&(z),&(w),&(a));
#define SLLLLLL(x,y,z,w,a,b) scanf("%lld %lld %lld %lld %lld %lld",&(x),&(y),&(z),&(w),&(a),&(b));

#define Pi(x) printf("%d\n",(x));
#define Pii(x,y) printf("%d %d\n",(x),(y));
#define Piii(x,y,z) printf("%d %d %d\n",(x),(y),(z));
#define Piiii(x,y,z,w) printf("%d %d %d %d\n",(x),(y),(z),(w));
#define Piiiii(a,b,c,d,e) printf("%d %d %d %d %d\n",(a),(b),(c),(d),(e));
#define Piiiiii(a,b,c,d,e,f) printf("%d %d %d %d %d %d\n",(a),(b),(c),(d),(e),(f));
#define PL(x) printf("%lld\n",(x)*1LL);
#define PLL(x,y) printf("%lld %lld\n",(x)*1LL,(y)*1LL);
#define PLLL(x,y,z) printf("%lld %lld %lld\n",(x)*1LL,(y)*1LL,(z)*1LL);
#define PLLLL(x,y,z,w) printf("%lld %lld %lld %lld\n",(x)*1LL,(y)*1LL,(z)*1LL,(w)*1LL);
#define PLLLLL(a,b,c,d,e) printf("%lld %lld %lld %lld %lld\n",(a),(b),(c),(d),(e));
#define PLLLLLL(a,b,c,d,e,f) printf("%lld %lld %lld %lld %lld %lld\n",(a),(b),(c),(d),(e),(f));

#define Pi1(x) printf("%d",  (x));
#define PiL(x) printf("%lld",(x));
#define Pspace putchar(' ');
#define Pendl  puts("");

#define MEM0(x) memset( (x), 0, sizeof( (x) ) )
#define MEM1(x) memset( (x),-1, sizeof( (x) ) )
#define REP1(i,n)  for (int i = 1; (n) >= i ; ++i)
#define REP0(i,n)  for (int i = 0; (n) >  i ; ++i)
#define REP(L,R,k) for (int i = (L); (R) >= i; i+= (k) )

int myRnd(int L,int R) {
    return abs(( (rand()<<15)|rand() ) ) % (R-L+1) + L;
}

const int N = 56;

int rnd1[N];
int rnd2[N];

map<LL,int> mp[N];

int p[N];

vint G[N];

bool vis[N];
int cnt[N];

void dfs(int now,int depth) {
    vis[now] = 1;
    cnt[depth]++;
    for (int i=0;SZ(G[now])>i;i++) {
        int ii=G[now][i];
        if (vis[ii]) continue;
        dfs(ii,depth+1);
    }
}

int main () {
    srand(7122);
    REP0(i,N)
    {
        rnd1[i] = myRnd(0,(1LL<<28)-1);
        rnd2[i] = myRnd(0,(1LL<<28)-1);
    }
    int q;
    Si(q);
    REP1(i,q)
    {
        int n;
        Si(n);
        for (int i=1;n>=i;i++) {
            int x;
            scanf("%d",&x);
            if (x!=0) {
                G[x].PB(i);
                G[i].PB(x);
            }
        }
        LL now=0;
        for (int i=1;n>=i;i++) {
            MEM0(cnt);
            MEM0(vis);
            dfs(i,1);
            LL tmp=0;
            REP0(j,N)
            {
                if (cnt[j] == 0) continue;
                tmp += (rnd2[ cnt[j] ] * rnd1[j]);
            }
            now += tmp;
        }
        int ret=mp[n][now];
        if (ret == 0) {
            mp[n][now] = i;
            printf("%d\n",i);
        }
        else {
            printf("%d\n",ret);
        }
        for (int i=0;n>=i;i++) {
            G[i].clear();
        }
    }
}

沒有留言:

張貼留言