超时算法,利用2的特殊性,用2个multiset来维护。单个multiset维护没法立即找到中位数。
其实也可以只用1个multiset,用一个中位指针,++,--来维护中位数。
#include<iostream> #include<stdio.h> #include<math.h> #include<string.h> #include<stdlib.h> #include<algorithm> #include<queue> #include<vector> #include<string> #include<map> #include<stack> #include<set> using namespace std; typedef long long ll; const int maxn = 1e4 + 7; int n; multiset<int> up, lo; stack<int> sta; void adapt() { int cnt = up.size() + lo.size(); int upsz = ceil(cnt / 2.0); while (up.size() < upsz) { up.insert(*lo.begin()); lo.erase(lo.begin()); } while (up.size() > upsz) { int x = *up.rbegin(); lo.insert(x); up.erase(up.find(x)); } } void push(int x) { up.insert(x); adapt(); } int peek() { return *(up.rbegin()); } void pop(int x) { if (up.find(x) != up.end()) up.erase(up.find(x)); else lo.erase(lo.find(x)); adapt(); } int main() { freopen("in.txt", "r", stdin); cin >> n; while (sta.empty() == false) sta.pop(); up.clear(), lo.clear(); char cmd[13]; int x; while (n--) { cin >> cmd; if (cmd[1] != 'u') { if (lo.empty() && up.empty()) { puts("Invalid"); continue; } if (cmd[1] == 'o') { int x = sta.top(); sta.pop(); cout << x << endl; pop(x); } else if (cmd[1] == 'e') { cout << peek() << endl; } } else { cin >> x; sta.push(x); push(x); } } return 0; }
此题正解树状数组
#include<stdio.h> #include<cstring> #include<iostream> #include<string> using namespace std; const int N=100005; int c[N]; int lowbit(int i){ return i&(-i); } void add(int pos,int value){ while(pos<N){ c[pos]+=value; pos+=lowbit(pos); } } int sum(int pos){ int res=0; while(pos>0){ res+=c[pos]; pos-=lowbit(pos); } return res; } int find(int value){ int l=0,r=N-1,median,res; while(l<r-1){ if((l+r)%2==0) median=(l+r)/2; else median=(l+r-1)/2; res=sum(median); if(res<value) l=median; else r=median; } return l+1; } int main(){ //freopen("D://test.txt","r",stdin); char ss[20]; int stack[N],top=0,n,pos; memset(c,0,sizeof(c)); scanf("%d",&n); while(n--){ scanf("%s",ss); if(ss[1]=='u'){ scanf("%d",&pos); stack[++top]=pos; add(pos,1); }else if(ss[1]=='o'){ if(top==0){ printf("Invalid "); continue; } int out=stack[top]; add(out,-1); printf("%d ",stack[top--]); }else if(ss[1]=='e'){ if(top==0){ printf("Invalid "); continue; } int res; if(top%2==0) res=find(top/2); else res=find((top+1)/2); printf("%d ",res); }else{ printf("Invalid "); } } return 0; }
类似题目:zoj3612