Cod sursa(job #688660)

Utilizator valentin.harsanValentin Harsan valentin.harsan Data 23 februarie 2012 18:46:36
Problema Coduri Huffman Scor 100
Compilator cpp Status done
Runda Arhiva educationala Marime 1.82 kb
#include<iostream>
#include<fstream>
#include<queue>
using namespace std;

const long long N = 3000010;

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

struct per {
	long long val;
	int poz;
};

long long n,nr,bz[N],smax,vall[N];
int fs[N],fd[N],val[N];
queue<per> q1,q2;

inline void cr(const per &a, const per &b) {
	per t;
	
	t.val = a.val + b.val; t.poz = ++nr;
	fd[nr] = a.poz;
	fs[nr] = b.poz;
	
	if(vall[nr]==0)
		vall[nr] = t.val;
	
	if(q1.empty() && q2.empty())
		return;
	
	q2.push(t);
}

void df(int nod, int niv, long long b10) {
	
	if(nod!=nr)
		smax += vall[nod];
	
	if(nod<=n) {
		val[nod] = niv;
		bz[nod] = b10;
		
		return;
	}
	
	df(fd[nod], niv+1, b10*2 + 1);
	df(fs[nod], niv+1, b10*2);
}

int main() {
	int i,a;
	per t,t1,t2;
	
	in >> n;
	
	for(i=1;i<=n;++i) {
		in >> a;
		
		vall[i]=a;
		
		t.poz = i; t.val = a;
		q1.push(t);
	}
	
	nr = n;
	
	while(!q1.empty() || !q2.empty()) {
		if(q1.empty()) {
			t1=q2.front();
			q2.pop();
			
			t2=q2.front();
			q2.pop();
			
			cr(t1,t2);
			
			continue;
		}
		if(q2.empty()) {
			t1=q1.front();
			q1.pop();
			
			t2=q1.front();
			q1.pop();
			
			cr(t1,t2);
			
			continue;
		}
		
		if(q1.front().val > q2.front().val) {
			t1 = q2.front();
			q2.pop();
		}
		else {
			t1=q1.front();
			q1.pop();
		}
		
		if(q1.empty()) {
			t2 = q2.front();
			q2.pop();
			
			cr(t1,t2);
			
			continue;
		}
		if(q2.empty()) {
			t2 = q1.front();
			q1.pop();
			
			cr(t1,t2);
			continue;
		}
		
		if(q1.front().val > q2.front().val) {
			t2 = q2.front();
			q2.pop();
		}
		else {
			t2 = q1.front();
			q1.pop();
		}
		
		cr(t1,t2);
	}
	
	df(nr,0,0);
	
	out << smax << "\n";
	
	for(i=1;i<=n;++i)
		out << val[i] << " " << bz[i] << "\n";
	
	return 0;
}