/*摘自计蒜客:http://www.jisuanke.com/course/35/6525
*优先队列解决哈夫曼编码
*当哈夫曼树上结点总个数大于 1 时,哈夫曼树的 WPL,等于树上除根结点之外的所有结点的权值之和。如果结点总个数为 1,则哈夫曼树的 WPL 即为根结点权值。*每次从优先队列里取出两个权值最小的元素,累加元素权值后,将两个元素权值的和插入到优先队列里。重复上述操作,直到优先队列里剩下一个元素为止。如果n为1,则需要特殊处理。
*维护一个小根堆
*/
#include<iostream>
using namespace std;
class Heap {
private:
int *data, size;
public:
Heap(int length_input) {
data = new int[length_input];
size = 0;
}
~Heap() {
delete[] data;
}
void push(int value) {
data[size] = value;
int current = size;
int father = (current - 1) / 2;
while (data[current] < data[father]) {
swap(data[current], data[father]);
current = father;
father = (current - 1) / 2;
}
size++;
}
int top() {
return data[0];
}
void update(int pos, int n) {
int lchild = 2 * pos + 1, rchild = 2 * pos + 2;
int max_value = pos;
if (lchild < n && data[lchild] < data[max_value]) {
max_value = lchild;
}
if (rchild < n && data[rchild] < data[max_value]) {
max_value = rchild;
}
if (max_value != pos) {
swap(data[pos], data[max_value]);
update(max_value, n);
}
}
void pop() {
swap(data[0], data[size - 1]);
size--;
update(0, size);
}
int heap_size() {
return size;
}
};
int main() {
//n:一共有n个数,value代表权值,这里代表每个字符出现次数,ans记录最后的结果。
int n,value, ans=0;
cin >> n;
Heap heap(n);
for (int i=1; i<=n; ++i) {
cin >> value;
heap.push(value);
}
if (n==1) {
ans += heap.top();
}
while(heap.heap_size() > 1) {
int a = heap.top();
heap.pop();
int b = heap.top();
heap.pop();
ans = ans + a + b;
heap.push(a + b);
}
cout << ans << endl;
return 0;
}