洛谷P1168 中位数
题目描述
给出一个长度为N的非负整数序列A[i],对于所有1 ≤ k ≤ (N + 1) / 2,输出A[1], A[2], …, A[2k - 1]的中位数。[color=red]即[/color]前1,3,5,……个数的中位数。
输入输出格式
输入格式:
输入文件median.in的第1行为一个正整数N,表示了序列长度。
第2行包含N个非负整数A[i] (A[i] ≤ 10^9)。
输出格式:
输出文件median.out包含(N + 1) / 2行,第i行为A[1], A[2], …, A[2i – 1]的中位数。
输入输出样例
输入样例#1:
7 1 3 5 7 9 11 6
输出样例#1:
1 3 5 6
说明
对于20%的数据,N ≤ 100;
对于40%的数据,N ≤ 3000;
对于100%的数据,N ≤ 100000。
用treap写中位数。
1 /*by SilverN*/ 2 #include<algorithm> 3 #include<iostream> 4 #include<cstring> 5 #include<cstdio> 6 #include<cmath> 7 #include<vector> 8 using namespace std; 9 const int mxn=120010; 10 int read(){ 11 int x=0,f=1;char ch=getchar(); 12 while(ch<'0' || ch>'9'){if(ch=='-')f=-1;ch=getchar();} 13 while(ch>='0' && ch<='9'){x=x*10+ch-'0';ch=getchar();} 14 return x*f; 15 } 16 int n; 17 struct node{ 18 int lc,rc; 19 int rand,size; 20 int cnt,w; 21 }t[mxn]; 22 int nct=0,rot=0; 23 void update(int rt){ 24 t[rt].size=t[t[rt].lc].size+t[t[rt].rc].size+t[rt].cnt; 25 return; 26 } 27 void rturn(int &rt){ 28 int tmp=t[rt].lc; 29 t[rt].lc=t[tmp].rc; 30 t[tmp].rc=rt; 31 update(rt);update(tmp); 32 rt=tmp; 33 return; 34 } 35 void lturn(int &rt){ 36 int tmp=t[rt].rc; 37 t[rt].rc=t[tmp].lc; 38 t[tmp].lc=rt; 39 update(rt);update(tmp); 40 rt=tmp; 41 return; 42 } 43 void add(int &rt,int v){ 44 if(!rt){ 45 rt=++nct; 46 t[rt].w=v; 47 t[rt].cnt=1; 48 t[rt].rand=rand(); 49 t[rt].size=1; 50 t[rt].lc=t[rt].rc=0; 51 return; 52 } 53 t[rt].size++; 54 if(t[rt].w==v) t[rt].cnt++; 55 else if(v<t[rt].w){ 56 add(t[rt].lc,v); 57 if(t[rt].rand>t[t[rt].lc].rand)rturn(rt); 58 } 59 else { 60 add(t[rt].rc,v); 61 if(t[rt].rand>t[t[rt].rc].rand)lturn(rt); 62 } 63 return; 64 } 65 int query(int rt,int k){ 66 if(k<=t[t[rt].lc].size)return query(t[rt].lc,k); 67 if(k>t[t[rt].lc].size+t[rt].cnt)return query(t[rt].rc,k-t[t[rt].lc].size-t[rt].cnt); 68 return t[rt].w; 69 } 70 int main(){ 71 n=read(); 72 int i,j,x; 73 srand(n+5); 74 for(i=1;i<=n;i++){ 75 x=read(); 76 add(rot,x); 77 if(i&1)printf("%d\n",query(rot,(i+1)/2)); 78 } 79 return 0; 80 }
本文为博主原创文章,转载请注明出处。