Cod sursa(job #2727435)

Utilizator ionanghelinaIonut Anghelina ionanghelina Data 21 martie 2021 21:05:12
Problema Coduri Huffman Scor 100
Compilator cpp-64 Status done
Runda Arhiva educationala Marime 3.12 kb
#include<bits/stdc++.h>
using namespace std;

const int maxN=(1e6)+5;


deque<pair<int,int> > q,q2;
//vector<pair<int,pair<int,long long> > > sol;
pair<int,long long> sol[maxN];


bool cmp(pair<int,pair<int,int> > a,pair<int,pair<int,int> > b)
{
    return a.second.second<b.second.second;
}

int g[maxN][2],n;

int frecv[maxN];

long long ans=0;

void dfs(int node,int len,long long code)
{
    if(node<=n)
    {
        sol[node]=make_pair(len,code);
        ans=ans+1LL*frecv[node]*len;

        return;
    }
    dfs(g[node-n][0],len+1,code*2LL);
    dfs(g[node-n][1],len+1,code*2LL+1LL);

}

char buff[100005];
const int dim=(1e5);
int pos=0;

void read(int &nr)
{
    nr=0;
    while(!isdigit(buff[pos]))
    {
        pos++;
        if(pos==dim)
        {
            pos=0;
            fread(buff,1,dim,stdin);
        }
    }

    while(isdigit(buff[pos]))
    {
        nr=nr*10+buff[pos]-'0';
        pos++;
        if(pos==dim)
        {
            pos=0;
            fread(buff,1,dim,stdin);
        }
    }
}
pair<int,pair<int,int> > vect[5];
int main()
{
    freopen("huffman.in","r",stdin);
    freopen("huffman.out","w",stdout);


    fread(buff,1,dim,stdin);

    read(n);


    for(int i=1;i<=n;i++)
    {
        int x;
        //scanf("%d",&x);
        read(x);

        frecv[i]=x;
        q.push_back(make_pair(i,x));
    }


    int currentNode=n;

    while(1)
    {
        //for the current Minimum
        int dvect=0;

        int cnt=0;

        while(!q.empty() && cnt<2)
        {
            vect[++dvect]=make_pair(1,q.front());
            q.pop_front();
            cnt++;
        }

        cnt=0;


        while(!q2.empty() && cnt<2)
        {
            vect[++dvect]=make_pair(2,q2.front());
            q2.pop_front();
            cnt++;
        }

        reverse(vect+1,vect+dvect+1);

        for(int i=1;i<=dvect;i++)
            if(vect[i].first==1) q.push_front(vect[i].second);
            else q2.push_front(vect[i].second);

        reverse(vect+1,vect+dvect+1);

        if(dvect<2)
            break;

        //stable_sort(vect.begin(),vect.end(),cmp);



        pair<int,pair<int,int> > pr1={0,{0,INT_MAX}};
        pair<int,pair<int,int> > pr2={0,{0,INT_MAX}};

        for(int i=1;i<=dvect;i++)
            if(vect[i].second.second<pr1.second.second)
            {

                pr2=pr1;
                pr1=vect[i];
            }
            else if(vect[i].second.second<pr2.second.second)
            {

                pr2=vect[i];
            }

        if(pr1.first==1) q.pop_front();
        else q2.pop_front();
        if(pr2.first==1) q.pop_front();
        else q2.pop_front();

        currentNode++;

        g[currentNode-n][0]=pr1.second.first;
        g[currentNode-n][1]=pr2.second.first;

        q2.push_back(make_pair(currentNode,pr1.second.second+pr2.second.second));

    }


    dfs(currentNode,0,0);

    printf("%lld\n",ans);


    for(int i=1;i<=n;i++)
    {
        printf("%d %lld\n",sol[i].first,sol[i].second);
    }
    return 0;
}