题意:给定一个n * n(1 <= n <= 10)的网格,有些已经填上了一些大写字母,需要补充完所有的字母,使每两两相邻的格子中的字母不同,且从上至下,从左至右,组成一个字符串后字典序最小。
由于组成字符串后的长度都为n * n,故字典序越往前的字母决定的优先级越大,所以贪心即可,从上到下,从左到右的补充格子里的字母,尽可能的使当前可以补充的字母尽量小。
#include<cstdio>
#include<cstring>
#include<cctype>
#include<cstdlib>
#include<cmath>
#include<iostream>
#include<sstream>
#include<iterator>
#include<algorithm>
#include<string>
#include<vector>
#include<set>
#include<map>
#include<deque>
#include<queue>
#include<stack>
#include<list>
#define fin freopen("in.txt", "r", stdin)
#define fout freopen("out.txt", "w", stdout)
#define pr(x) cout << #x << " : " << x << " "
#define prln(x) cout << #x << " : " << x << endl
typedef long long ll;
typedef unsigned long long llu;
const int INT_INF = 0x3f3f3f3f;
const int INT_M_INF = 0x7f7f7f7f;
const ll LL_INF = 0x3f3f3f3f3f3f3f3f;
const ll LL_M_INF = 0x7f7f7f7f7f7f7f7f;
const double pi = acos(-1.0);
const double EPS = 1e-6;
const int dx[] = {0, 0, -1, 1};
const int dy[] = {-1, 1, 0, 0};
const ll MOD = 1e9 + 7;
const int MAXN = 10 + 10;
const int MAXT = 10000 + 10;
using namespace std;
int T, n;
char tu[MAXN][MAXN];
int main(){
int kase = 0;
scanf("%d", &T);
while(T--){
scanf("%d", &n);
for(int i = 0; i < n; ++i) scanf("%s", tu[i]);
for(int i = 0; i < n; ++i)
for(int j = 0; j < n; ++j){
if(tu[i][j] != '.') continue;
for(char ch = 'A'; ch <= 'Z'; ++ch){
bool flag = true;
for(int k = 0; k < 4; ++k)
if(i + dx[k] >= 0 && i + dx[k] < n && j + dy[k] >= 0 && j + dy[k] <= n && tu[i + dx[k]][j + dy[k]] == ch){
flag = false;
break;
}
if(flag){
tu[i][j] = ch;
break;
}
}
}
printf("Case %d:\n", ++kase);
for(int i = 0; i < n; ++i) printf("%s\n", tu[i]);
}
return 0;
}