#include <vector> #include <queue> #include <iostream> #include <fstream>
using namespace std;
int R, C; typedef struct Cluster { int min_x, min_y, max_x, max_y; int num_of_stars; Cluster() : min_x(-1), min_y(-1), max_x(-1), max_y(-1), num_of_stars(0) {} } Cluster; typedef struct Point { int x; int y; Point(int x, int y) : x(x), y(y) {} } Point; vector<vector<char>> sky; vector<vector<short>> mark; vector<Cluster> clusters(505); char p[550]; int idx; void calculate_bound(int x, int y) { clusters[idx].min_x = clusters[idx].min_x == -1 ? x : std::min(x, clusters[idx].min_x); clusters[idx].min_y = clusters[idx].min_y == -1 ? y : std::min(y, clusters[idx].min_y); clusters[idx].max_x = clusters[idx].max_x == -1 ? x : std::max(x, clusters[idx].max_x); clusters[idx].max_y = clusters[idx].max_y == -1 ? y : std::max(y, clusters[idx].max_y); }
int flood_fill(int x, int y, int index) { int num_of_stars = 1; mark[x][y] = index; calculate_bound(x, y); queue<Point> q; q.push(Point(x, y)); while (!q.empty()) { auto p = q.front(); q.pop(); for (int i = -1; i <= 1; ++i) { for (int j = -1; j <= 1; ++j) { int xx = p.x + i, yy = p.y + j; if (xx < 0 || xx >= R || yy < 0 || yy >= C) continue; if (sky[xx][yy] != '1' || mark[xx][yy] != -1) continue; ++num_of_stars; mark[xx][yy] = index; calculate_bound(xx, yy); q.push(Point(xx, yy)); } } } return num_of_stars; }
void rotate(vector<vector<char>> &cluster, int lx, int ly) { int rows = (int)cluster.size(), cols = (int)cluster[0].size(); vector<vector<char>> t(rows, vector<char>(cols)); for(int i = 0; i < lx; ++i) { for(int j = 0; j < ly; ++j) { t[j][lx - i - 1] = cluster[i][j]; } } for(int i = 0; i < ly; ++i) { for(int j = 0; j < lx; ++j) { cluster[i][j] = t[i][j]; } } }
void mirror(vector<vector<char>> &cluster, int lx, int ly) { for(int i = 0; i < lx; ++i) { for(int j = 0; j < ly/2; ++j) { swap(cluster[i][j], cluster[i][ly - 1 - j]); } } }
bool match(int index, vector<vector<char>> cluster, int lx, int ly) { for(int i = 0; i < lx; ++i) { for(int j = 0; j < ly; ++j) { int xx = clusters[index].min_x + i, yy = clusters[index].min_y + j; if(mark[xx][yy] == index && cluster[i][j] == '0') return false; } } return true; }
bool is_two_cluster_same(int a, int b) { if (clusters[a].num_of_stars != clusters[b].num_of_stars) { return false; } int ax = clusters[a].max_x - clusters[a].min_x + 1, ay = clusters[a].max_y - clusters[a].min_y + 1; int lx = clusters[b].max_x - clusters[b].min_x + 1, ly = clusters[b].max_y - clusters[b].min_y + 1; vector<vector<char>> tmp(110, vector<char>(110)); for (int i = 0; i < lx; ++i) { for (int j = 0; j < ly; ++j) { int xx = i + clusters[b].min_x, yy = j + clusters[b].min_y; tmp[i][j] = sky[xx][yy]; } } if (ax == lx && ay == ly && match(a, tmp, lx, ly)) return true; for(int i = 0; i < 4; ++i) { rotate(tmp, lx, ly); swap(lx, ly); if(ax == lx && ay == ly && match(a, tmp, lx, ly)) return true; } mirror(tmp, lx, ly); for(int i = 0; i < 4; ++i) { rotate(tmp, lx, ly); swap(lx, ly); if(ax == lx && ay == ly && match(a, tmp, lx, ly)) return true; } return false; }
int main() { ifstream fin("starry.in"); ofstream fout("starry.out"); fin >> C >> R; sky = vector<vector<char>>(R, vector<char>(C)); mark = vector<vector<short>>(R, vector<short>(C, -1)); for (int i = 0; i < R; ++i) { for (int j = 0; j < C; ++j) { fin >> sky[i][j]; } } idx = 0; for (int i = 0; i < R; ++i) { for (int j = 0; j < C; ++j) { if (sky[i][j] == '1' && mark[i][j] == -1) { int num_of_stars = flood_fill(i, j, idx); clusters[idx].num_of_stars = num_of_stars; ++idx; cout << idx - 1 << " : stars " << num_of_stars << endl; } } } char c = 'a'; vector<vector<char>> ans = sky; for(int i = 0; i < idx; ++i) { int index = -1; for(int j = 0; j < i; ++j) { if(is_two_cluster_same(i, j)) { index = j; cout << i << " and " << j << " same!" << endl; break; } } if(index != -1) { p[i] = p[index]; } else { p[i] = c++; } for(int ii = clusters[i].min_x; ii <= clusters[i].max_x; ++ii) { for(int jj = clusters[i].min_y; jj <= clusters[i].max_y; ++jj) { if(mark[ii][jj] == i) { ans[ii][jj] = p[i]; } } } } for(int i = 0; i < R; ++i) { for(int j = 0; j < C; ++j) { fout << ans[i][j]; cout << ans[i][j]; } fout << endl; cout << endl; } }
|