Cod sursa(job #2911472)

Utilizator AndreiCroitoruAndrei Croitoru AndreiCroitoru Data 29 iunie 2022 20:40:30
Problema Coduri Huffman Scor 80
Compilator cpp-64 Status done
Runda Arhiva educationala Marime 2.83 kb
#include <bits/stdc++.h>
#define int long long
using namespace std;

/**
create a priority queue Q consisting of each unique character.
sort then in ascending order of their frequencies.
for all the unique characters:
    create a newNode
    extract minimum value from Q and assign it to leftChild of newNode
    extract minimum value from Q and assign it to rightChild of newNode
    calculate the sum of these two minimum values and assign it to the value of newNode
    insert this newNode into the tree
return rootNode
*/





int const N = 1e6 + 1;
struct node
{
    int value;
    int st, dr, lvl;

} huffmanTree[2 * N];
int n;
void dfs(int nod, int nivel, int val)
{
    if(nod <= n)
    {
        huffmanTree[nod].lvl = nivel;
        huffmanTree[nod].value = val;
        return;
    }
    dfs(huffmanTree[nod].st, nivel + 1, val * 2);
    dfs(huffmanTree[nod].dr, nivel + 1, val * 2 + 1);
}


int32_t main()
{

    ifstream cin("huffman.in");
    ofstream cout("huffman.out");

    int ans = 0;
    cin >> n;
    for(int i = 1; i <= n; i++)
    {
        cin >> huffmanTree[i].value; // sortat crescator
    }
    int inceput = 1;
    int sfarsit = n;
    int inceput2 = n + 1;
    int sfarsit2 = n;
    while(inceput <= sfarsit or inceput2 < sfarsit2)
    {
        int st, dr;
        if(inceput <= sfarsit and inceput2 <= sfarsit2)
        {
            if(huffmanTree[inceput].value <= huffmanTree[inceput2].value)
            {
                st = inceput;
                inceput ++;
            }
            else
            {
                st = inceput2;
                inceput2 ++;
            }
        }
        else if(inceput <= sfarsit)
        {
            st = inceput;
            inceput++;
        }
        else
        {
            st = inceput2;
            inceput2 ++;
        }
        if(inceput <= sfarsit and inceput2 <= sfarsit2)
        {
            if(huffmanTree[inceput].value <= huffmanTree[inceput2].value)
            {
                dr = inceput;
                inceput ++;
            }
            else
            {
                dr = inceput2;
                inceput2 ++;
            }
        }
        else if(inceput <= sfarsit)
        {
            dr = inceput;
            inceput ++;
        }
        else
        {
            dr = inceput2;
            inceput2 ++;
        }
        huffmanTree[++sfarsit2].st = st;
        huffmanTree[sfarsit2].dr = dr;
        huffmanTree[sfarsit2].value = huffmanTree[st].value + huffmanTree[dr].value;
        ans += huffmanTree[sfarsit2].value;

    }
    dfs(sfarsit2, 0, 1);
    cout << ans << '\n'; // numarul de caractere
    for(int i = 1; i <= n; i++)
    {
        cout << huffmanTree[i].lvl << " " << huffmanTree[i].value << '\n';
    }
    return 0;
}