【题解】P9464 [EGOI 2023] Padel Prize Pursuit / 追梦笼式网球
题意
有
思路
可以发现
其中节点左边为
通过记录
代码
#include<bits/stdc++.h>
//#pragma GCC optimize(1,2,3,"Ofast","inline")
using namespace std;
const int N=2e5+5,inf=1e9+5;
struct sgt
{
int maxn,id;
friend const sgt operator+(const sgt ls,const sgt rs);
const sgt operator+=(const sgt x){return(*this)=(*this)+x;}
};
const sgt operator+(const sgt ls,const sgt rs)
{
if(ls.maxn>=rs.maxn)return ls;
return rs;
}
class segment_tree
{
#define ls (u<<1)
#define rs (u<<1|1)
private:
sgt node[N<<2];
void push_up(int u){node[u]=node[ls]+node[rs];}
public:
void init(int u,int l,int r)
{
if(l==r)node[u].id=l;
else
{
int mid=l+r>>1;
init(ls,l,mid),init(rs,mid+1,r);
push_up(u);
}
}
void update(int u,int l,int r,int x,int k)
{
if(l==r)node[u].maxn+=k;
else
{
int mid=l+r>>1;
if(x<=mid)update(ls,l,mid,x,k);
else update(rs,mid+1,r,x,k);
push_up(u);
}
}
sgt query(){return node[1];}
#undef ls
#undef rs
}tree;
vector<int>edge[N];
void build(int u,int v){edge[u].emplace_back(v);}
int id[N],val[N],num[N],lst[N],ans[N];
bool vis[N];
void dfs(int n,int u)
{
vis[u]=true;
tree.update(1,1,n,id[u],val[u]);
ans[tree.query().id]++;
for(int v:edge[u])dfs(n,v);
tree.update(1,1,n,id[u],-val[u]);
}
void solve()
{
int n,m;
cin>>n>>m;
for(int i=1,x,y;i<=m;i++)
{
cin>>x>>y,x++,y++;
if(lst[x]!=0)val[num[x]]=i-lst[x],build(i,num[x]);
if(lst[y]!=0)val[num[y]]=i-lst[y],build(i,num[y]),num[y]=lst[y]=0;
lst[x]=i,num[x]=i,id[i]=x;
}
tree.init(1,1,n);
for(int i=1;i<=n;i++)
if(num[i]&&!vis[num[i]])val[num[i]]=m-lst[i]+1,dfs(n,num[i]);
for(int i=1;i<=n;i++)cout<<ans[i]<<' ';
}
signed main()
{
ios::sync_with_stdio(false);
cin.tie(0);
// freopen("ybt.in","r",stdin);
// freopen("ybt.out","w",stdout);
int T=1;
for(;T;T--)solve();
return 0;
}