Cod sursa(job #120756)

Utilizator bogdan2412Bogdan-Cristian Tataroiu bogdan2412 Data 6 ianuarie 2008 15:22:19
Problema NKPerm Scor 30
Compilator cpp Status done
Runda Arhiva de probleme Marime 1.98 kb
#include <cstdio>
#include <map>

using namespace std;

map< pair<int, int>, int > M;

const int MAXN = 32;
const long long MAX = 1LL << 55;

int N, K, T;
int v[MAXN];

inline int codif( int v[] )
{
	int rez = 0;
	for (int i = 0; i < N; i++)
		rez = rez * (K + 1) + v[i];
	return rez;
}

inline void decodif( int val, int v[] )
{
	for (int i = N - 1; i >= 0; i--)
		v[i] = val % (K + 1),
		val /= (K + 1);
}

inline long long get( int st, int last )
{
	if (M.find( make_pair(st, last) ) != M.end())
		return M[ make_pair(st, last) ];

	long long Rez = 0; int v[MAXN];
	decodif( st, v );
	for (int i = 0; i < N; i++)
		if (v[i] > 0 && i != last)
		{
			v[i]--;
			Rez += get( codif(v), i );
			if (Rez > MAX)
			{
				Rez = MAX;
				break;
			}
			v[i]++;
		}

	for (int i = 0; i < N; i++)

	M.insert( make_pair( make_pair(st, last), Rez ) );
	return Rez;
}

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

	scanf("%d %d %d", &N, &K, &T);
	for (int i = 0; i < N; i++)
		M[ make_pair(0, i) ] = 1,
		v[i] = K;

	get( codif(v), -1 );

	for (; T; T--)
	{
		char c;
		scanf(" %c", &c);
		if (c == 'A')
		{
			long long Nr = 0;
			for (int i = 0; i < N; i++)
				v[i] = K;

			int last = -1;
			for (int i = 0; i < N * K; i++)
			{
				int val;
				scanf("%d", &val);
				val--;

				for (int a = 0; a < val; a++)
				{
					if (v[a] == 0 || a == last) continue;

					v[a]--;
					Nr += M[ make_pair( codif(v), a ) ];
					v[a]++;
				}
				v[ val ]--; last = val;
			}
			printf("%lld\n", Nr + 1);
		}
		if (c == 'B')
		{
			long long Nr;
			scanf("%lld", &Nr);

			for (int i = 0; i < N; i++)
				v[i] = K;
			
			int last = -1;
			for (int left = N * K; left; left--)
				for (int k = 0; k < N; k++)
					if (v[k] > 0 && k != last)
					{
						v[k]--;
						if (M[ make_pair( codif(v), k ) ] < Nr)
							Nr -= M[ make_pair( codif(v), k ) ];
						else
						{
							printf("%d ", k + 1);
							last = k;
							break;
						}
						v[k]++;
					}
			printf("\n");
		}
	}

	return 0;
}