Problem:
Problem K: Cat Numbers!

ねこのアリストテレスは数学の問題を考えるのを趣味にしている。今彼が考えている問題は以下のようなものである。

1以上の自然数 A, B (A < B) に対して、A から B までの自然数の和を C、A と B を十進表記して A, B の順に結合したものを D とすると、両者が等しくなることがある。たとえば1から5までの和は15、2から7までの和は27、7から119までの和は 7119、といった具合である。このような A と B のペアのことを cat numbers と呼ぶことにする。アリストテレスは、A と B の桁数が与えられたときに、cat numbersを全て列挙したい、と考えた。

アリストテレスは、A または B を固定した場合に解が存在するかどうかを確かめる方法は思いついたので、小さい桁数に対しては答えを得ることができた。しかし、桁数が大きくなるにしたがって計算をするのが大変になり、途中でうんざりして投げ出してしまった。そこで、あなたにお願いがある。アリストテレスに代わって、指定された桁数のcat numbersを全て列挙するプログラムを書いてほしい。

Input

入力は1行のみからなる。A の桁数 a および B の桁数 b が1つの空白文字で区切られて与えられる。これらは 1 ≤ a ≤ b ≤ 16 を満たす。

Output

指定された桁数のcat numbersを、A が小さいものから順に出力せよ。A が同じものが複数ある場合は、B が小さいものから出力せよ。各行には1つのcat numbersにおける A と B を1つの空白文字で区切ったものを出力せよ。また、条件に合うcat numbersが存在しない場合は "No cats." と1行に出力せよ。

Notes on Submission

上記形式で複数のデータセットが与えられます。入力データの 1 行目にデータセットの数が与えられます。各データセットに対する出力を上記形式で順番に出力するプログラムを作成して下さい。

Sample Input

4
1 1
1 3
1 4
2 2

Output for the Sample Input

1 5
2 7
7 119
No cats.
13 53
18 63
33 88
35 91

Solution in C (judge verdict: Accepted)

// AOJ 2195: Cat Numbers!
// 2017.12.10

#include <stdio.h>
#include <stdlib.h>

int f[17][10] = {{0},
{2,5,3},
{2,5,3,11},
{2,5,3,37},
{2,5,3,11,101},
{2,5,3,41,271},
{2,5,3,7,11,13,37},
{2,5,3,239,4649},
{2,5,3,11,73,101,137},
{2,5,3,37,333667},
{2,5,3,11,41,271,9091},
{2,5,3,21649,513239},
{2,5,3,7,11,13,37,101,9901},
{2,5,3,53,79,265371653},
{2,5,3,11,239,4649,909091},
{2,5,3,31,37,41,271,2906161},
{2,5,3,11,17,73,101,137,5882353}};

int p[17][10] = {{0},
{1,1,2},
{2,2,2,1},
{3,3,3,1},
{4,4,2,1,1},
{5,5,2,1,1},
{6,6,3,1,1,1,1},
{7,7,2,1,1},
{8,8,2,1,1,1,1},
{9,9,4,1,1},
{10,10,2,1,1,1,1},
{11,11,2,1,1},
{12,12,3,1,1,1,1,1,1},
{13,13,2,1,1,1},
{14,14,2,1,1,1,1},
{15,15,3,1,1,1,1,1},
{16,16,2,1,1,1,1,1,1}};

long long fp[17][10] = {{0},
{2, 5, 9},
{4, 25, 9, 11},
{8, 125, 27, 37},
{16, 625, 9, 11, 101},
{32, 3125, 9, 41, 271},
{64, 15625, 27, 7, 11, 13, 37},
{128, 78125, 9, 239, 4649},
{256, 390625, 9, 11, 73, 101, 137},
{512, 1953125, 81, 37, 333667},
{1024, 9765625, 9, 11, 41, 271, 9091},
{2048, 48828125, 9, 21649, 513239},
{4096, 244140625LL, 27, 7, 11, 13, 37, 101, 9901},
{8192, 1220703125LL, 9, 53, 79, 265371653LL},
{16384, 6103515625LL, 9, 11, 239, 4649, 909091},
{32768, 30517578125LL, 27, 31, 37, 41, 271, 2906161},
{65536, 152587890625LL, 9, 11, 17, 73, 101, 137, 5882353}};

long long tens[17];

int a, b;

typedef struct { long long A, B; } T;
T ans[500]; int sz;

int cmp(T *a, T *b)
{
	if (a->A - b->A) { if (a->A < b->A) return -1; else return 1; }
	if (a->B < b->B) return -1;
	return 1;
}

void check(long long x, long long y)
{
	long long A, B;

	A = x+y+1, B = y-x+1;
	if ((A & 1) || (B & 1)) return;
	A = (A >> 1) - tens[b];
	if (A < tens[a-1] || A >= tens[a]) return;
	B >>= 1;
	if (B < tens[b-1] || B >= tens[b]) return;

	ans[sz].A = A, ans[sz++].B = B;
}

void rec(int k, long long x, long long y)
{

	int i;
	long long s, t;

	if (!f[b][k]) {
		if (x >= tens[b-1])	check(x, y);
		return;
	}
	rec(k+1, x, y);
	s = fp[b][k], t = f[b][k];
	rec(k+1, x, y*s);
	for (i = 0; i < p[b][k]; i++) {
		x *= t;
		s /= t;
		if (x >= tens[b]) break;
		rec(k+1, x, y*s);
	}
}

int main()
{
	int cno, i;
	long long x;

	for (x = 1, i = 0; i <= 16; i++, x *= 10) tens[i] = x;

    scanf("%d", &cno);
	while (cno--) {
		scanf("%d%d", &a, &b);
		sz = 0;
		rec(0, 1, 1);

		qsort(ans, sz, sizeof(T), cmp);
		if (!sz) puts("No cats.");
		else for (i = 0; i < sz; i++) printf("%lld %lld\n", ans[i].A, ans[i].B);
	}
	return 0;
}