线段树模拟
#include<cstdio> using namespace std; int sz[20000005]; void update(int t){ sz[t]=sz[t<<1]+sz[t<<1|1]; } void build(int t,int l,int r){ if (l==r){ sz[t]=1; return; } int mid=(l+r)>>1; build(t<<1,l,mid); build(t<<1|1,mid+1,r); update(t); } void modify(int t,int l,int r,int x){ if (l==r){ sz[t]=0; return; } int mid=(l+r)>>1; if (x<=mid) modify(t<<1,l,mid,x); else modify(t<<1|1,mid+1,r,x); update(t); } int query_suf(int t,int l,int r,int x){ if (l==r) return 0; int mid=(l+r)>>1; if (x<=mid) return sz[t<<1|1]+query_suf(t<<1,l,mid,x); else return query_suf(t<<1|1,mid+1,r,x); } int query_pre(int t,int l,int r,int x){ if (l==r) return sz[t]; int mid=(l+r)>>1; if (x<=mid) return query_pre(t<<1,l,mid,x); else return sz[t<<1]+query_pre(t<<1|1,mid+1,r,x); } int query_Kth(int t,int l,int r,int K){ if (l==r) return l; int mid=(l+r)>>1; if (K<=sz[t<<1]) return query_Kth(t<<1,l,mid,K); else return query_Kth(t<<1|1,mid+1,r,K-sz[t<<1]); } int main(){ int n; scanf("%d",&n); int last=0,m=n; build(1,0,n-1); for (int i=1; i<=n; i++){ int x; scanf("%d",&x); x%=m; m--; int ID=query_suf(1,0,n-1,last); if (ID>=x){ int now=query_pre(1,0,n-1,last); now+=x; last=query_Kth(1,0,n-1,now); } else{ x-=ID; last=query_Kth(1,0,n-1,x); } int now=query_pre(1,0,n-1,last); modify(1,0,n-1,last); printf("%d ",last+1); if (now>m) now=1; last=query_Kth(1,0,n-1,now); } return 0; }