Cod sursa(job #393154)

Utilizator Mishu91Andrei Misarca Mishu91 Data 8 februarie 2010 22:43:58
Problema Nums Scor 0
Compilator cpp Status done
Runda porc_ag Marime 1.75 kb
#include <cstdio>
#include <cstring>

const int MAX_N = 100005;

typedef struct nod
{
	int nr;
	nod *fiu[10];

	nod()
	{
		nr = 0;
//		memset(fiu, 0, sizeof fiu);
	}
}*Trie;
Trie T[MAX_N];

int M, N, V[MAX_N], A[MAX_N];
char S[MAX_N];

inline int lsb(int x)
{
	return (x & -x);
}

void update(int poz)
{
	for(; poz < MAX_N; poz += lsb(poz))
		++A[poz];
}

int sum(int poz)
{
	int rez = 0;
	for(; poz; poz -= lsb(poz))
		rez += A[poz];
	return rez;
}

void insert(Trie &T, char *s, int lev)
{
	if(lev == M)
	{
		T -> nr = 1;
		return;
	}

	if(T -> fiu[*s - '0'] == NULL)
		T -> fiu[*s-'0'] = new nod;
	
	insert(T -> fiu[*s-'0'], s+1, lev+1);
	for(int i = 0; i < 10; ++i)
		if(T -> fiu[i])
			T -> nr += T -> fiu[i] -> nr;
}

void baga(char *s)
{
	if(V[M] == 0)
		T[M] = new nod;
	++V[M];
	update(M);
	insert(T[M], s, 0);
}

void search(Trie &T, int k, int lev)
{
	if(k == 0) return;

	for(int i = 0; i < 10; ++i)
		if(T -> fiu[i])
			if(T -> fiu[i] -> nr < k)
				k -= T -> fiu[i] -> nr;
			else
			{
				S[lev] = i + '0';
		//		fprintf(stderr, "%d %c\n", lev, i+'0');
				search(T -> fiu[i], k, lev+1);
				return;
			}
}

void query(int K)
{
	int lg = (1 << 17), i = 0;

	for(; lg; lg >>= 1)
		if(i + lg < MAX_N && sum(i + lg) < K)
			i += lg;

	K -= sum(i);
//	fprintf(stderr, "%d %d\n", i+1, K);
	search(T[i+1], K, 0);
	S[i+1] = 0;

	printf("%s\n", S);
}

int main()
{
	freopen("nums.in","rt",stdin);
	freopen("nums.out","wt",stdout);

	scanf("%d\n", &N);

	for(int i = 1; i <= N; ++i)
	{
		char buf[MAX_N];
		fgets(buf, MAX_N, stdin);

		M = strlen(buf);
		if(buf[M-1] == '\n')
			--M;
		M -= 2;
		if(buf[0] == '1')
			baga(buf+2);
		else
		{
			int K = 0, i = 2;
			while(buf[i] != '\n' && buf[i] != 0)
				K = K*10 + buf[i++]-'0';

			//fprintf(stderr, "%d\n", K);

			query(K);
		}
	}
}