洛谷P3295 [SCOI2016]萌萌哒

倍增加并查集

复杂度 \(O(nlog^2n)\)

虽然AC了,可是一个月后重新看到他还是不会做

直接贴题解

#include<bits/stdc++.h>
using namespace std;

#define go(i,a,b) for(int i=a;i<=b;++i)
#define com(i,a,b) for(int i=a;i>=b;--i)
#define mem(a,b) memset(a,b,sizeof(a))

const int inf=0x3f3f3f3f,N=1e5+10,mod=1e9+7;

int f[N][18],n,m;

inline void read(int &x){
    x=0;char c=getchar(),f=1;
    while(!isdigit(c)){ if(c=='-') f=-1; c=getchar(); }
    while(isdigit(c)){ x=x*10+c-'0'; c=getchar(); }
    x*=f;
}

int find(int x,int i){
    return f[x][i]=f[x][i]==x?x:find(f[x][i],i);
}

void merge(int x,int y,int i){
    x=find(x,i),y=find(y,i);
    if(x==y) return;
    f[y][i]=x;
}

signed main(){
    //freopen("input.txt","r",stdin);
    read(n),read(m);
    int l1,l2,r1,r2;
    const int t=log2(n);
    go(i,1,n)
        go(j,0,t)
            f[i][j]=i;
    go(i,1,m){
        read(l1),read(r1),read(l2),read(r2);
        com(j,t,0){
            if(l1+(1<<j)-1>r1) continue;
            merge(l1,l2,j);
            l1+=1<<j;l2+=1<<j;
        }
    }
    com(k,t,1){
        go(i,1,n-(1<<k)+1){
            int j=find(i,k);
            merge(i,j,k-1);
            merge(i+(1<<k-1),j+(1<<k-1),k-1);
        }
    }
    int ans=0;
    go(i,1,n){
        if(find(i,0)==i) ans=ans==0?9:ans=((long long)ans*10)%mod;
    }
    cout<<ans;
    return 0;
}

猜你喜欢

转载自www.cnblogs.com/White-star/p/11759107.html
今日推荐