题目描述
给定一个数列,初始为空,请支持下面三种操作:
- 给定一个整数 xx,请将 xx 加入到数列中。
- 输出数列中最小的数。
- 删除数列中最小的数(如果有多个数最小,只删除 11 个)。
输入格式
第一行是一个整数,表示操作的次数 nn。
接下来 nn 行,每行表示一次操作。每行首先有一个整数 opop 表示操作类型。
- 若 op = 1op=1,则后面有一个整数 xx,表示要将 xx 加入数列。
- 若 op = 2op=2,则表示要求输出数列中的最小数。
- 若 op = 3op=3,则表示删除数列中的最小数。如果有多个数最小,只删除 11 个。
输出格式
对于每个操作 22,输出一行一个整数表示答案。
输入输出样例
输入 #1
5 1 2 1 5 2 3 2
输出 #1
2 5
说明/提示
数据规模与约定
- 对于 30\%30% 的数据,保证 n leq 15n≤15。
- 对于 70\%70% 的数据,保证 n leq 10^4n≤104。
- 对于 100\%100% 的数据,保证 1 leq n leq 10^61≤n≤106,1 leq x lt 2^{31}1≤x<231,op in {1, 2, 3}op∈{1,2,3}。
1 #include <iostream> 2 #include <cstdio> 3 #include <algorithm> 4 #include <cstring> 5 #include <string> 6 using namespace std; 7 8 const int N = 1000001; 9 int heap[N], n, ans; 10 int tot; 11 12 void down(int k){ 13 int l = k*2; 14 int r = k*2 + 1; 15 if(l > tot) return; 16 if(heap[l] < heap[k] || heap[r] < heap[k]){ 17 if(heap[l] < heap[r]){ 18 swap(heap[l], heap[k]); 19 down(l); 20 }else{ 21 swap(heap[r], heap[k]); 22 down(r); 23 } 24 } 25 } 26 27 void up(int k){ 28 if(k == 1) 29 return; 30 if(heap[k] < heap[k>>1]){ 31 swap(heap[k], heap[k>>1]); 32 up(k>>1); 33 } 34 } 35 36 void push(int x){ 37 heap[++tot] = x; 38 up(tot); 39 } 40 41 int pop(){ 42 int x = heap[1]; 43 heap[1] = heap[tot--]; 44 down(1); 45 return x; 46 } 47 48 int main(){ 49 memset(heap, 127, sizeof(heap)); 50 scanf("%d", &n); 51 for(int i=1;i<=n;i++){ 52 int x; 53 scanf("%d", &x); 54 if(x == 1){ 55 int tmp; 56 scanf("%d", &tmp); 57 push(tmp); 58 } 59 if(x == 2){ 60 printf("%d ", heap[1]); 61 } 62 if(x == 3){ 63 pop(); 64 } 65 66 } 67 68 return 0; 69 }