[] JZOJ6368 quality tree (tree)

description

God has big hands wyp binary trees, each point has a right to the point. This tree is the god wyp quality tree, because
just to find two different points u, v, as long as u is v ancestors, have the right to meet the points u and v are relatively prime.
Now that you know a great God peeking through wyp preorder point the weight of the tree, you want to restore the Great God
wyp tree, or point out impossible.
Read the sample in order to better understand the problem.


analysis

  • First preprocessed prime number for each number, prime factor decomposition can

  • Then each bucket before and after a scan are again drawn back farthest forward position of each number in the interval thereto are coprime

  • If for \ ([l, r] \ ) interval, a viable location enumeration \ (I \) , split into \ ([L,. 1-I], [I +. 1, R & lt] \) , the complexity of the \ (O (n ^ 2) \ )

  • However, if both the head and the tail to the middle to find each layer halve the length of the search, the complexity of the \ (O (n \ log_2n) \)


code

#pragma GCC optimize("O3")
#pragma G++ optimize("O3")
#include<stdio.h>
#include<string.h>
#include<algorithm>
#define MAXN 1000005
#define MAX 10000005
#define ll long long
#define reg register ll
#define ha 1926081719491001
#define fo(i,a,b) for (reg i=a;i<=b;++i)
#define fd(i,a,b) for (reg i=a;i>=b;--i)

using namespace std;

bool bz[MAX];
ll left[MAXN],right[MAXN];
ll a[MAXN],p[MAX],bucket[MAX],fa[MAXN],mxp[MAX];
ll n,tot,flag=1;

inline ll read()
{
    ll x=0,f=1;char ch=getchar();
    while (ch<'0' || '9'<ch){if (ch=='-')f=-1;ch=getchar();}
    while ('0'<=ch && ch<='9')x=x*10+ch-'0',ch=getchar();
    return x*f;
}
inline ll max(ll x,ll y){return x>y?x:y;}
inline ll min(ll x,ll y){return x<y?x:y;}
inline void init()
{
    #define MAXX 10000000
    memset(bz,1,sizeof(bz));
    fo(i,2,MAXX)
    {
        if (bz[i])p[++tot]=i,mxp[i]=i;
        for (reg j=1;j<=tot && i*p[j]<=MAXX;++j)
        {bz[i*p[j]]=0,mxp[i*p[j]]=p[j];if (i%p[j]==0)break;}
    }
}
inline bool judge(ll i,ll l,ll r)
{
    if (left[i]<=l && right[i]>=r)return 1;
    return 0;
}
inline void dfs(ll l,ll r,ll x)
{
    if (l>r)return;
    if (l==r){fa[l]=x;return;}
    fo(len,0,(r-l)/2)
    {
        ll i=l+len,j=r-len;
        if (judge(i,l,r))
        {
            fa[i]=x,dfs(l,i-1,i),dfs(i+1,r,i);
            return;
        }
        if (judge(j,l,r))
        {
            fa[j]=x,dfs(l,j-1,j),dfs(j+1,r,j);
            return;
        }
    }
    flag=0;return;
}
int main()
{
    //freopen("T3.in","r",stdin);
    freopen("tree.in","r",stdin);
    freopen("tree.out","w",stdout);
    n=read(),init();fo(i,1,n)a[i]=read();
    fo(i,1,n)
    {
        ll x=a[i];left[i]=1;
        while (x>1)
        {
            ll tmp=mxp[x];
            left[i]=max(left[i],bucket[tmp]?bucket[tmp]+1:1);
            bucket[tmp]=i;
            while (x%tmp==0)x/=tmp;
        }
    }
    memset(bucket,0,sizeof(bucket));
    fd(i,n,1)
    {
        ll x=a[i];right[i]=n;
        while (x>1)
        {
            ll tmp=mxp[x];
            right[i]=min(right[i],bucket[tmp]?bucket[tmp]-1:n);
            bucket[tmp]=i;
            while (x%tmp==0)x/=tmp;
        }
    }
    tot=0,dfs(1,n,0);
    if (!flag){printf("impossible\n");return 0;}
    fo(i,1,n)printf("%lld ",fa[i]);
    return 0;
}

Guess you like

Origin www.cnblogs.com/horizonwd/p/11610005.html