#include<bits/stdc++.h>
#define N 300000
#define Log 20
#define B 1100
#define S 600
#define NM 600
using namespace std;
inline int Read()
{int x=0;char c=getchar();for(;c<48||c>57;c=getchar());
for(;c>=48&&c<=57;c=getchar())x=(x<<1)+(x<<3)+(c^48);return x;}
struct inside{
int n,nm,I[N+5],L[NM+5],R[NM+5],appn[NM+5],app[N+5];
inline void init(int x)
{
n=x;nm=(n+S-1)/S;
for(int i=1;i<=nm;i++)
L[i]=i*S-S+1,R[i]=i*S;
R[nm]=n;
for(int i=1;i<=n;i++)
I[i]=(i+S-1)/S;
}
inline void add(int x)
{
// if(FLAG) return;
appn[I[x]]-=app[x];
app[x]^=1;
appn[I[x]]+=app[x];
}
inline int force(int x,int y)
{
for(int i=x;i<=y;i++) if(app[i]) return i;
return -1;
}
inline int query(int x,int y)
{
// if(FLAG) return 0;
if(I[x]==I[y]) return force(x,y);
int tmp=force(x,R[I[x]]);
if(tmp!=-1) return tmp;
tmp=force(L[I[y]],y);
if(tmp!=-1) return tmp;
for(int i=I[x]+1;i<=I[y]-1;i++)
if(appn[i]) return force(L[i],R[i]);
return -1;
}
};
struct query{
int id,x,y,l,r,lca;
};
inline bool cmp1(query x,query y)
{
int xk=x.l/B,yk=y.l/B;
if(xk!=yk) return xk<yk;
if(xk&1) return x.r<y.r;
return x.r>y.r;
}
struct ljb{
int en,v[2*N+5],fst[N+5],nxt[2*N+5];
inline void add(int x,int y)
{
en++;
v[en]=y;
nxt[en]=fst[x];
fst[x]=en;
}
};
ljb g;
query q[N+5];
inside d;
int n,m,now,ans[N+5],c[N+5],dfn[2*N+5],dfl[N+5],dfr[N+5],fa[N+5][Log+5],dep[N+5];
int nm,I[N+5],L[NM+5],R[NM+5],appn[NM+5],app[N+5];
inline void dfs(int x,int f)
{
// cout<<x<<' '<<f<<' '<<now<<endl;
fa[x][0]=f;
dep[x]=dep[f]+1;
dfn[++now]=c[x];
dfl[x]=now;
for(int i=g.fst[x];i;i=g.nxt[i])
if(g.v[i]!=f) dfs(g.v[i],x);
dfn[++now]=c[x];
dfr[x]=now;
}
inline int LCA(int x,int y)
{
if(dep[x]<dep[y]) swap(x,y);
for(int i=Log;i>=0;i--)
if(dep[fa[x][i]]>=dep[y]) x=fa[x][i];
if(x==y) return x;
for(int i=Log;i>=0;i--)
if(fa[x][i]!=fa[y][i])
x=fa[x][i],y=fa[y][i];
return fa[x][0];
}
inline void init()
{
nm=(n+S-1)/S;
for(int i=1;i<=nm;i++)
L[i]=i*S-S+1,R[i]=i*S;
R[nm]=n;
for(int i=1;i<=n;i++)
I[i]=(i+S-1)/S;
}
inline void add(int x)
{
// if(FLAG) return;
appn[I[x]]-=app[x];
app[x]^=1;
appn[I[x]]+=app[x];
}
inline int force(int x,int y)
{
for(int i=x;i<=y;i++) if(app[i]) return i;
return -1;
}
inline int query(int x,int y)
{
// if(FLAG) return 0;
if(I[x]==I[y]) return force(x,y);
int tmp=force(x,R[I[x]]);
if(tmp!=-1) return tmp;
tmp=force(L[I[y]],y);
if(tmp!=-1) return tmp;
for(int i=I[x]+1;i<=I[y]-1;i++)
if(appn[i]) return force(L[i],R[i]);
return -1;
}
int main()
{
cin>>n>>m;
d.init(n);
for(int i=1;i<=n;i++)
c[i]=Read();
for(int i=1;i<n;i++)
{
int x=Read(),y=Read();
g.add(x,y),g.add(y,x);
}
dfs(1,0);
for(int i=1;i<=Log;i++)
for(int x=1;x<=n;x++)
fa[x][i]=fa[fa[x][i-1]][i-1];
for(int i=1;i<=m;i++)
{
int x=Read(),y=Read(),l=Read(),r=Read();
q[i].id=i,q[i].l=l,q[i].r=r;
if(dfl[x]>dfl[y]) swap(x,y);
int lca=LCA(x,y);
if(lca==x) q[i].x=dfl[x],q[i].y=dfl[y],q[i].lca=0;
else q[i].x=dfr[x],q[i].y=dfl[y],q[i].lca=c[lca];
}
sort(q+1,q+1+m,cmp1);
for(int i=1,x=1,y=0;i<=m;i++)
{
while(x>q[i].x) add(dfn[--x]);
while(y<q[i].y) add(dfn[++y]);
while(x<q[i].x) add(dfn[x++]);
while(y>q[i].y) add(dfn[y--]);
if(q[i].lca) add(q[i].lca);
ans[q[i].id]=query(q[i].l,q[i].r);
if(q[i].lca) add(q[i].lca);
}
for(int i=1;i<=m;i++)
printf("%d\n",ans[i]);
return 0;
}
卡在 #7,死活过不去……