Cod sursa(job #2281405)

Utilizator mircearoataMircea Roata Palade mircearoata Data 12 noiembrie 2018 10:39:18
Problema Coduri Huffman Scor 30
Compilator cpp-64 Status done
Runda Arhiva educationala Marime 1.44 kb
#include <cstdio>
#include <queue>

using namespace std;

int n, nrNod;
bool ok = 1;

int fiust[2000001], fiudr[2000001], aparitii[2000001];
int len[1000001], x1, x2;
long long ans[1000001], sum;

void dfs(int nod, long long val, int l)
{
    if(nod <= n)
    {
        len[nod] = l;
        ans[nod] = val;
        return;
    }
    dfs(fiust[nod], (val << 1), l+1);
    dfs(fiudr[nod], (val << 1) + 1, l+1);
}

class Compare
{
public:
    bool operator() (int l, int r)
    {
        return aparitii[l] > aparitii[r];
    }
};

priority_queue <int, vector<int>, Compare> pq;

int main()
{
    FILE *in = fopen("huffman.in", "r");
    FILE *out = fopen("huffman.out", "w");
    fscanf(in, "%d", &n);
    nrNod = n;
    for(int i = 1; i <= n; i++)
    {
        fscanf(in, "%d", &aparitii[i]);
        pq.push(i);
    }
    while(ok)
    {
        x1 = pq.top();
        pq.pop();
        if(pq.empty())
            ok = 0;
        else
        {
            x2 = pq.top();
            pq.pop();
            nrNod++;
            fiust[nrNod] = x1;
            fiudr[nrNod] = x2;
            aparitii[nrNod] = aparitii[x1]+aparitii[x2];
            pq.push(nrNod);
        }
    }
    dfs(nrNod, 0, 0);
    for(int i = 1; i <= n; i++)
        sum += aparitii[i] * len[i];
    fprintf(out, "%I64d\n", sum);
    for(int i = 1; i <= n; i++)
        fprintf(out, "%d %I64d\n", len[i], ans[i]);
    return 0;
}