1 #include <iostream>
2 #include <cstdlib>
3 #include <cstdio>
4 #include <cstring>
5 #include <string>
6 #include <vector>
7 #include <iterator>
8 #include <stack>
9 #include <algorithm>
10
11 using namespace std;
12
13 const int N = 100010;
14
15 typedef struct LeftHeap *Lefh;
16
17 Lefh Merge_node(Lefh, Lefh); // 驱动Merge
18 static Lefh Merge(Lefh, Lefh); // 实际Merge
19 Lefh inst(int, Lefh); // 插入操作 视为 单节点堆与左式堆Merge
20 Lefh DelteMin(Lefh); // 删除最小元 视为 删掉根而得到两个堆,再把两者Merge
21 void print(Lefh) // bfs打印堆
22
23 struct LeftHeap
24 {
25 int val;
26 Lefh l;
27 Lefh r;
28 int npl;
29 };
30
31 Lefh q[N];
32
33 Lefh Merge_node(Lefh h1, Lefh h2)
34 {
35 if (h1 == NULL) return h2;
36 if (h2 == NULL) return h1;
37 if (h1 -> val < h2 -> val)
38 return Merge(h1, h2);
39 else
40 return Merge(h2, h1);
41 }
42
43 static Lefh Merge(Lefh h1, Lefh h2)
44 {
45 if (h1 -> l == NULL) h1 -> l = h2; // 由此可以看出 Merge为O(logN)---合并堆的过程中,递归的次数取决于最右路径的长度,根据左式堆的结构性其最右路径最长为logN
46 else
47 {
48 h1 -> r = Merge_node(h1 -> r, h2);
49 if (h1 -> l -> npl < h1 -> r -> npl) // 交换左右儿子
50 {
51 Lefh tmp = h1 -> l;
52 h1 -> l = h1 -> r;
53 h1 -> r = tmp;
54 }
55
56 h1 -> npl = h1 -> r -> npl + 1; // 左式堆:根节点及其左右儿子中,必定是 右儿子的npl最小,则根的npl 多1
57 }
58
59 return h1;
60 }
61
62 Lefh inst(int x, Lefh h)
63 {
64 Lefh t = (struct LeftHeap*) malloc(sizeof (LeftHeap));
65
66 t -> val = x;
67 t -> npl = 0;
68 t -> l = t -> r = NULL;
69 h = Merge_node(t, h); // 单节点当成一棵子树插入
70
71 return h;
72 }
73
74 Lefh DelteMin(Lefh h)
75 {
76 Lefh t = h;
77 if (h -> l && !(h -> r)) h = h -> l; // 只有左儿子
78 else h = Merge_node(h -> l, h -> r);
79 free(t);
80 return h;
81 }
82
83 void print(Lefh h)
84 {
85 // bfs遍历树
86
87 // 标记法:方便判断节点的顺序(徒手画图) 表示当前节点不存在左儿子或右儿子 就将 左儿子或右儿子标记为-1
88 Lefh ept = (struct LeftHeap*) malloc(sizeof (LeftHeap));
89 ept -> val = -1;
90 ept -> l = ept -> r = NULL;
91 ept -> npl = -1;
92
93 int hh = 1, tt = 0;
94 q[++ tt] = h;
95
96 while (hh <= tt)
97 {
98 Lefh t = q[hh ++];
99 printf("(%d,%d) ", t -> val, t -> npl);
100
101 if (t -> val == -1) continue;
102 if (t -> l) q[++ tt] = t -> l; else q[++ tt] = ept;
103 if (t -> r) q[++ tt] = t -> r; else q[++ tt] = ept;
104 }puts("");
105 }
106
107 int main()
108 {
109 int n, m, x;
110 cin >> n >> m;
111 Lefh h1 = NULL, h2 = NULL;
112 for (int i = 0; i < n; i ++)
113 {
114 scanf("%d", &x);
115 h1 = inst(x, h1);
116 }
117 for (int i = 0; i < m; i ++)
118 {
119 scanf("%d", &x);
120 h2 = inst(x, h2);
121 }
122 print(h1);
123 print(h2);
124
125 Lefh H = Merge_node(h1, h2);
126 print(H);
127
128 H = DelteMin(H);
129 print(H);
130
131
132 return 0;
133 }