Pagini recente » Cod sursa (job #352731) | Cod sursa (job #2458795) | Cod sursa (job #3267248) | Cod sursa (job #996138) | Cod sursa (job #1211488)
#include <algorithm>
#include <cstdio>
#include <vector>
#include <queue>
using namespace std;
class Huffman {
public:
Huffman(const int _Base = 0, const vector<int> &_Values = vector<int>()):
Base(_Base),
OriginalSize(_Values.size()),
Size(GetSize(Base, _Values.size())),
Cost(0LL),
Nodes(vector<Node>(Size, Node(0, Base)))
{
queue< pair<int, long long> > Q1, Q2;
for (int i = 0; i < OriginalSize; i++)
Nodes[i].value = _Values[i];
for (int i = 0; i < Size; i++)
Q1.push(make_pair(i, Nodes[i].value));
while (int(Q1.size() + Q2.size()) >= Base)
{
Size++;
Nodes.push_back(Node(0, Base));
for (int i = 0; i < Base; i++)
{
if (!Q1.empty() && (Q2.empty() || Q1.front().second < Q2.front().second))
{
Nodes.back().value += Q1.front().second;
Nodes.back().sons[i] = Q1.front().first;
Q1.pop();
}
else
{
Nodes.back().value += Q2.front().second;
Nodes.back().sons[i] = Q2.front().first;
Q2.pop();
}
}
Q2.push(make_pair(Size - 1, Nodes.back().value));
Cost += Nodes.back().value;
}
}
vector< pair<int, long long> > getStrings() const {
queue< pair<int, pair<long long, int>> > Q;
Q.push(make_pair(Size - 1, make_pair(0, 0)));
vector< pair<int, long long> > ret(OriginalSize);
while (!Q.empty())
{
const int node = Q.front().first, level = Q.front().second.second;
const long long code = Q.front().second.first;
Q.pop();
int Psize = GetSize(Base, OriginalSize);
if (node < Psize)
{
if (node < OriginalSize)
ret[node] = make_pair(level, code);
continue;
}
for (int i = 0; i < Base; i++)
Q.push(make_pair(Nodes[node].sons[i], make_pair(code * Base + i, level + 1)));
}
return ret;
}
int size() const {
return OriginalSize;
}
int actual_size() const {
return Size;
}
long long cost() const {
return Cost;
}
private:
class Node {
public:
long long value;
vector<int> sons;
Node(const long long _value = 0, const int sons_count = 0):
value(_value),
sons(vector<int>(sons_count, 0)) {}
};
int Base;
int OriginalSize, Size;
long long Cost;
vector<Node> Nodes;
static int GetSize(const int Base, const int Size) {
return (Size - 3 + Base) / (Base - 1) * (Base - 1) + 1;
}
};
int main()
{
freopen("huffman.in", "r", stdin);
freopen("huffman.out", "w", stdout);
int N;
scanf("%d", &N);
vector<int> Values(N);
for (int i = 0; i < int(Values.size()); i++)
scanf("%d", &Values[i]);
Huffman T = Huffman(2, Values);
printf("%lld\n", T.cost());
vector< pair<int, long long> > Ans = T.getStrings();
for (const auto p: Ans)
printf("%d %lld\n", p.first, p.second);
}