D. Restore Permutation
题链
不难看出我们应该从后往前做
我们设t[i]=i*(i-1)/2
最后一个i肯定能在t数组直接找到
比如我们找到了是3
那么要是我们下一个是5
我们就要把这个3从以后的t[4] t[5] ....中剪掉
注意这里剪掉之后我们t还是保持单调性 这里我们应该很敏感的可以知道查找一个t=a[i]可以用二分了
注意code里t[i]数组是tr[i]的前缀和
int n,tr[N];
int lowbit(int x){return x&-x;}
void add(int x,int c){
for(int i=x;i<=n;i+=lowbit(i)){
tr[i]+=c;
}
}
int query(int x){
int res=0;
for(int i=x;i;i-=lowbit(i)){
res+=tr[i];
}
return res;
}
void solve(){
cin>>n;
vector<int>a(n+1),ans(n+1);
for(int i=1;i<=n;i++)cin>>a[i],add(i,i);
for(int i=n;i>=1;i--){
int l=1,r=n;
while(l<r){
int mid=(l+r+1)>>1;
if(query(mid-1)<=a[i])l=mid;
else r=mid-1;
}
ans[i]=l;
add(l,-l);
}
for(int i=1;i<=n;i++)cout<<ans[i]<<' ';
}
标签:Manthan,rated,int,tr,everyone,Div,open
From: https://www.cnblogs.com/ycllz/p/17004756.html