标签:
题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=5249
思路分析:使用queue记录管道中的值并使用treap能够查询第K大的功能查询第floor(m/2)+1大的数值;
对于in value操作,将value插入queue中和treap中;对于out操作,在treap中删除queue中队头元素,并在queue中使队头元素出队;
对于query操作,因为tail – head的值即为管道中的值的个数,使用treap查询第floor((tail – head) / 2) + 1大的元素即可;
代码如下:
#include <cstdio> #include <ctime> #include <cstring> #include <iostream> using namespace std; const int MAX_N = 10000 + 100; int queue[MAX_N]; struct Node{ Node *ch[2]; int value, key; int size; int cmp(int x) const{ if (x == value) return -1; return x < value ? 0 : 1; } void Maintain(){ size = 1; if (ch[0] != NULL) size += ch[0]->size; if (ch[1] != NULL) size += ch[1]->size; } }; void Rotate(Node *&o, int d){ Node *k = o->ch[d ^ 1]; o->ch[d ^ 1] = k->ch[d]; k->ch[d] = o; o->Maintain(); k->Maintain(); o = k; } void Insert(Node *&o, int x){ if (o == NULL){ o = new Node(); o->ch[0] = o->ch[1] = NULL; o->value = x; o->key = rand(); } else{ int d = (x < (o->value) ? 0 : 1); Insert(o->ch[d], x); if (o->ch[d]->key > o->key) Rotate(o, d ^ 1); } o->Maintain(); } void Remove(Node *&o, int x){ int d = o->cmp(x); if (d == -1){ Node *u = o; if (o->ch[0] != NULL && o->ch[1] != NULL){ int d2 = (o->ch[0]->key > o->ch[1]->key ? 1 : 0); Rotate(o, d2); Remove(o->ch[d2], x); }else{ if (o->ch[0] == NULL) o = o->ch[1]; else o = o->ch[0]; delete u; } }else Remove(o->ch[d], x); if (o != NULL) o->Maintain( ); } int Find(Node *o, int x){ while (o != NULL){ int d = o->cmp(x); if (d == -1) return 1; else o = o->ch[d]; } return 0; } int FindKth(Node *o, int k){ int l_size = (o->ch[0] == NULL ? 0 : o->ch[0]->size); if (k == l_size + 1) return o->value; else if (k <= l_size) return FindKth(o->ch[0], k); else return FindKth(o->ch[1], k - l_size - 1); } void MakeEmpty(Node *root){ if (root == NULL) return; if (root->ch[0]) MakeEmpty(root->ch[0]); if (root->ch[1]) MakeEmpty(root->ch[1]); delete root; } int main(){ int n, case_id = 0, value; srand(100); while (scanf("%d", &n) != EOF){ Node *root = NULL; int head = 0, tail = 0, ans; char str[10]; printf("Case #%d:\n", ++case_id); for (int i = 0; i < n; ++i){ scanf("%s", str); if (str[0] == ‘i‘){ scanf("%d", &value); queue[tail++] = value; Insert(root, value); } else if (str[0] == ‘o‘) Remove(root, queue[head++]); else{ ans = FindKth(root, (tail - head) / 2 + 1); printf("%d\n", ans); } } MakeEmpty(root); } return 0; }
标签:
原文地址:http://www.cnblogs.com/tallisHe/p/4584287.html