1. 程式人生 > >[Usaco2003 Open]Lost Cows

[Usaco2003 Open]Lost Cows

body pac site too play 中比 man mat this

Description
N (2 <= N <= 8,000) cows have unique brands in the range 1..N. In a spectacular display of poor judgment, they visited the neighborhood ‘watering hole‘ and drank a few too many beers before dinner. When it was time to line up for their evening meal, they did not line up in the required ascending numerical order of their brands.Regrettably, FJ does not have a way to sort them. Furthermore, he‘s not very good at observing problems. Instead of writing down each cow‘s brand, he determined a rather silly statistic: For each cow in line, he knows the number of cows that precede that cow in line that do, in fact, have smaller brands than that cow.Given this data, tell FJ the exact ordering of the cows.
1~n,亂序排列,告訴每個位置的前面的數字中比它小的數的個數,求每個位置的數字是多少

Input

  • Line 1: A single integer, N
  • Lines 2..N: These N-1 lines describe the number of cows that precede a given cow in line and have
    brands smaller than that cow. Of course, no cows precede the first cow in line, so she is not listed
    . Line 2 of the input describes the number of preceding cows whose brands are smaller than the cow i
    n slot #2; line 3 describes the number of preceding cows whose brands are smaller than the cow in sl
    ot #3; and so on.

Output

  • Lines 1..N: Each of the N lines of output tells the brand of a cow in line. Line #1 of the output
    tells the brand of the first cow in line; line 2 tells the brand of the second cow; and so on.

Sample Input
5
1
2
1
0

Sample Output
2
4
5
3
1

一個比較有趣的題目,線段樹裏面維護當前區間內還有多少個數,每次從找出原序列最後一個數(因為不會對其他數造成影響)

至於怎麽找數?在線段樹裏找到第k大的數,這是非常簡單的

(ps:這題除了用到線段樹思想外,就和線段樹沒有任何關系了……)

#include<cmath>
#include<cstdio>
#include<cstring>
#include<iostream>
#include<algorithm>
using namespace std;
const int N=8e3;
int tree[N*3+10],a[N+10],ans[N+10];
inline int read(){
    int x=0,f=1;char ch=getchar();
    for (;ch<‘0‘||ch>‘9‘;ch=getchar())    if (ch==‘-‘)    f=-1;
    for (;ch>=‘0‘&&ch<=‘9‘;ch=getchar())  x=x*10+ch-‘0‘;
    return x*f;
}
#define ls (p<<1)
#define rs (p<<1|1)
void build(int p,int l,int r){
    tree[p]=r+1-l;
    if (l==r)   return;
    int mid=(l+r)>>1;
    build(ls,l,mid),build(rs,mid+1,r);
}
int query(int p,int l,int r,int t){
    tree[p]--;//記得減掉
    if (l==r)   return l;
    int mid=(l+r)>>1;
    return t<=tree[ls]?query(ls,l,mid,t):query(rs,mid+1,r,t-tree[ls]);//兩邊判斷查詢
}
int main(){
    int n=read();
    build(1,1,n);
    for (int i=2;i<=n;i++)   a[i]=read();
    for (int i=n;i;i--)     ans[i]=query(1,1,n,a[i]+1);//a[i]+1是其本身的位置
    for (int i=1;i<=n;i++)   printf("%d\n",ans[i]);
    return 0;
}

[Usaco2003 Open]Lost Cows