#include #include #include using namespace std; typedef vector vb; typedef vector vi; typedef vector vvi; vb R = { 0, 0, 1, 0, 0, 0, 1, 0, 1, 1, 0, 1, 0, 0, 1, 0 }; vb Q = { 1, 0, 1, 0, 0, 1, 1, 1, 1, 1, 0, 1, 0, 1, 1, 1 }; vb B = { 1, 0, 0, 0, 0, 1, 0, 1, 0, 0, 0, 0, 0, 1, 0, 1 }; vb N = { 0, 1, 0, 1, 1, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0 }; vb K = { 0, 0, 0, 0, 0, 1, 1, 1, 0, 1, 0, 1, 0, 1, 1, 1 }; void dfs(vvi& g, vb& v, vi& t, vi& q, int x) { v[x] = true; for (int y : g[x]) { if (v[y]) continue; t[y] = x; dfs(g, v, t, q, y); } q.push_back(x); } int main() { ios::sync_with_stdio(false); cin.tie(nullptr); int n; string c; cin >> n >> c; vb p; if (c == "R") p = R; else if (c == "Q") p = Q; else if (c == "B") p = B; else if (c == "N") p = N; else if (c == "K") p = K; vb a(n * n); for (int i = 0; i < n; i++) { string s; cin >> s; for (int j = 0; j < n; j++) a[n * i + j] = s[j] != '.'; } // zbudowanie grafu vvi g(n * n); vvi h(n * n); for (int i = 0; i < n; i++) { for (int j = 0; j < n; j++) { if (!a[n * i + j]) continue; for (int k = 0; k < 4; k++) { for (int l = 0; l < 4; l++) { if (!p[4 * k + l]) continue; int x = i + k - 2; int y = j + l - 2; if (x < 0 || x >= n || y < 0 || y >= n) continue; if (a[n * x + y]) { g[n * i + j].push_back(n * x + y); h[n * x + y].push_back(n * i + j); } } } } } // wybranie korzenia vb v(n * n, false); vi t(n * n); vi s; for (int x = 0; x < n * n; x++) { if (a[x] && !v[x]) dfs(g, v, t, s, x); } int r; v = vb(n * n, false); vi q; while (!s.empty()) { int x = s.back(); s.pop_back(); if (v[x]) continue; r = x; dfs(h, v, t, q, r); } // wyznaczenie drzewa v = vb(n * n, false); t = vi(n * n, -1); q = vi(); dfs(h, v, t, q, r); for (int x = 0; x < n * n; x++) { if (a[x] && x != r && t[x] == -1) { cout << "NO\n"; return 0; } } cout << "YES\n"; for (int x : q) { if (x == r) continue; int y = t[x]; cout << (x / n + 1) << " " << (x % n + 1) << " " << (y / n + 1) << " " << (y % n + 1) << "\n"; } return 0; }