結果
問題 | No.2981 Pack Tree into Grid |
ユーザー |
|
提出日時 | 2024-11-20 00:46:50 |
言語 | C++23 (gcc 13.3.0 + boost 1.87.0) |
結果 |
AC
|
実行時間 | 12 ms / 2,000 ms |
コード長 | 5,637 bytes |
コンパイル時間 | 3,820 ms |
コンパイル使用メモリ | 286,976 KB |
実行使用メモリ | 5,248 KB |
最終ジャッジ日時 | 2024-12-04 23:30:08 |
合計ジャッジ時間 | 6,216 ms |
ジャッジサーバーID (参考情報) |
judge5 / judge1 |
(要ログイン)
ファイルパターン | 結果 |
---|---|
sample | AC * 1 |
other | AC * 28 |
ソースコード
#include <bits/stdc++.h>using namespace std;struct Fast{Fast(){std::cin.tie(nullptr);ios::sync_with_stdio(false);cout << setprecision(10);}} fast;#define all(a) (a).begin(), (a).end()#define contains(a, x) ((a).find(x) != (a).end())#define rep(i, a, b) for (int i = (a); i < (int)(b); i++)using ll = long long;void calc_distance(const vector<vector<int>> &g, const int root, vector<int> &dist, vector<int> &prev, int &last_vertex){queue<int> qu;qu.push(root);dist[root] = 0;prev[root] = -1;while (!qu.empty()){auto x = qu.front();qu.pop();last_vertex = x;for (auto y : g[x])if (prev[x] != y){qu.push(y);dist[y] = dist[x] + 1;prev[y] = x;}}}pair<int, int> find_center(const vector<vector<int>> &g){int u, v;vector<int> dist(g.size(), 0), prev(g.size(), -1);calc_distance(g, 0, dist, prev, u);calc_distance(g, u, dist, prev, v);int d = dist[v] / 2, x = v;rep(i, 0, d) x = prev[x];return {x, (dist[v] & 1) ? prev[x] : -1};}bool solve_rooted(const int N, const vector<vector<int>> &T1, const vector<vector<int>> &T2, const vector<pair<int, int>> &T2_pos, const int T1_root,const int T2_root){if (T1_root == -1 || T2_root == -1) return false;const ll class_coeff = 1000;map<ll, int> class_map;class_map[0] = 1;auto dfs = [&](auto self, int x, int p, const vector<vector<int>> &T, vector<int> &class_ids) -> void{vector<int> children_ids;for (auto y : T[x]){if (y == p) continue;self(self, y, x, T, class_ids);children_ids.push_back(class_ids[y]);}sort(all(children_ids));ll children_id = 0;for (auto v : children_ids)children_id = children_id * class_coeff + v;if (!contains(class_map, children_id)) class_map[children_id] = class_map.size() + 1;class_ids[x] = class_map[children_id];};vector<int> T1_class_ids(T1.size(), -1), T2_class_ids(T2.size(), -1);dfs(dfs, T1_root, -1, T1, T1_class_ids);dfs(dfs, T2_root, -1, T2, T2_class_ids);if (T1_class_ids[T1_root] != T2_class_ids[T2_root]) return false;vector<pair<int, int>> ans(N, {-1, -1});auto dfs2 = [&](auto self, int x1, int p1, int x2, int p2) -> void{if (x1 < N) ans[x1] = T2_pos[x2];vector<pair<int, int>> children1, children2;for (auto y : T1[x1])if (y != p1) children1.push_back({T1_class_ids[y], y});for (auto y : T2[x2])if (y != p2) children2.push_back({T2_class_ids[y], y});sort(all(children1));sort(all(children2));rep(i, 0, children1.size()) self(self, children1[i].second, x1, children2[i].second, x2);};dfs2(dfs2, T1_root, -1, T2_root, -1);cout << "Yes" << "\n";rep(i, 0, N){auto [x, y] = ans[i];cout << (x + 1) << " " << (y + 1) << "\n";}return true;}void solve(){int N, H, W;cin >> N;vector<tuple<int, int, int>> T;rep(i, 0, N - 1){int u, v, w;cin >> u >> v >> w;T.push_back({u, v, w});}cin >> H >> W;vector<string> S(H);rep(i, 0, H) cin >> S[i];size_t T1_size = 1, T2_size = 0;for (auto [u, v, w] : T)T1_size += w;rep(i, 0, H) rep(j, 0, W) T2_size += S[i][j] == '#';if (T1_size != T2_size){cout << "No" << "\n";return;}vector<vector<int>> T1(T1_size, vector<int>()), T2(T2_size, vector<int>());vector<pair<int, int>> T2_pos;{size_t dummy = N;for (auto [u, v, w] : T){u--, v--;if (w == 1){T1[u].push_back(v), T1[v].push_back(u);}else{T1[u].push_back(dummy), T1[dummy].push_back(u);rep(i, 0, w - 2){T1[dummy].push_back(dummy + 1), T1[dummy + 1].push_back(dummy);dummy++;}T1[v].push_back(dummy), T1[dummy].push_back(v);dummy++;}}}{vector<vector<int>> T2_index(H, vector<int>(W, -1));rep(i, 0, H) rep(j, 0, W) if (S[i][j] == '#') T2_index[i][j] = T2_pos.size(), T2_pos.push_back({i, j});rep(i, 0, T2.size()){auto [x1, y1] = T2_pos[i];rep(k, 0, 4){int x2 = x1 + (k & 1 ? 0 : 1 - k);int y2 = y1 + (k & 1 ? 2 - k : 0);if (x2 < 0 || x2 >= H || y2 < 0 || y2 >= W) continue;if (T2_index[x2][y2] != -1) T2[i].push_back(T2_index[x2][y2]);}}}size_t T1_deg_max = 0, T2_deg_max = 0;rep(i, 0, T1_size) T1_deg_max = max(T1_deg_max, T1[i].size());rep(i, 0, T2_size) T2_deg_max = max(T2_deg_max, T2[i].size());if (T1_deg_max != T2_deg_max){cout << "No" << "\n";return;}auto [T1_c1, T1_c2] = find_center(T1);auto [T2_c1, T2_c2] = find_center(T2);if (solve_rooted(N, T1, T2, T2_pos, T1_c1, T2_c1)) return;if (solve_rooted(N, T1, T2, T2_pos, T1_c1, T2_c2)) return;if (solve_rooted(N, T1, T2, T2_pos, T1_c2, T2_c1)) return;if (solve_rooted(N, T1, T2, T2_pos, T1_c2, T2_c2)) return;cout << "No" << "\n";}int main(){int t = 1;cin >> t;while (t--)solve();}