CF1490D Permutation Transformation 题解
Content
给定一个排列 \(a\),按照以下方法构造一棵树:
- 选择当前排列中的最大数作为根的编号。
- 最大数左边的所有数按照上述方法建左子树,若没有数则该节点没有左儿子。
- 最大数右边的所有数按照上述方法建右子树,若没有数则该节点没有右儿子。
求每个结点的深度(根节点深度为 \(0\))。
数据范围:\(t\) 组数据,\(1\leqslant t\leqslant 100\),\(1\leqslant n\leqslant 100\)。
Solution
看到这个题目第一眼以为是什么神仙构造题,结果一看数据范围……直接上 dfs 就过了。
具体地,我们先从 \(1\) 到 \(n\) 进行遍历找到最大数,再将最大数左边的数和右边的数分别继续 dfs,直到左边界大于右边界为止,dfs 时再将每个节点的深度赋值,每递归一层,就相比于上一层 \(+1\) 即可。
如果没听懂就看代码吧。
Code
int a[107], d[107];
iv dfs(int l, int r, int cur) {
if(l > r) return;
int pl = l;
F(i, l, r) if(a[pl] < a[i]) pl = i;
d[pl] = cur;
dfs(l, pl - 1, cur + 1), dfs(pl + 1, r, cur + 1);
}
int main() {
MT {
F(i, 1, 100) d[i] = 0;
int n = Rint;
F(i, 1, n) a[i] = Rint;
dfs(1, n, 0);
F(i, 1, n) write(a[i]), putchar((i == n) ? ' ' : '\n');
}
return 0;
}

浙公网安备 33010602011771号