@Dmaxiya
2020-12-12T07:21:10.000000Z
字数 3701
阅读 1246
Codeforces
Contests 链接:Codeforces Round #453 (Div. 2)
过题数:3
排名:408/8956
的家在 处,他的朋友家在 处,他将要拜访这位朋友,在路上有 个传送点,每个传送点的位置是 ,每个传送点都有一个最远能够传送到的最右边的位置 ,它可以将 从 传送到 之间的任意一点,问 是否可以只通过传送点就到达他的朋友家。
第一行为两个整数 ,接下去 行每行两个整数 ,对于每一个 ,都满足 。
如果 可以只通过传送点就到达他的朋友家,输出 ,否则输出 ,大小写任意。
| 输入 | 输出 | 提示 |
|---|---|---|
| 3 5 0 2 2 4 3 5 |
YES | 如图:![]() 可以从 到达 ,然后通过第二个传送点到达 ,再通过第三个传送点到达 。 |
| 3 7 0 4 2 5 6 7 |
NO | 如图:![]() 无法从 通过传送点到达他的朋友家。 |
按照题意模拟,从 开始,尽量往远处跑,最后能够跑到的点只要大于等于 ,就输出 。
#include <iostream>#include <cstdio>#include <cstdlib>#include <cmath>#include <climits>#include <cfloat>#include <cstring>#include <string>#include <vector>#include <list>#include <queue>#include <stack>#include <map>#include <set>#include <algorithm>using namespace std;#define LL long longint n, m, a, b, ans;int main() {#ifdef Dmaxiyafreopen("test.txt", "r", stdin);#endif // Dmaxiyaios::sync_with_stdio(false);while(scanf("%d%d", &n, &m) != EOF) {ans = 0;for(int i = 0; i < n; ++i) {scanf("%d%d", &a, &b);if(ans >= a) {ans = max(ans, b);}}if(ans >= m) {printf("YES\n");} else {printf("NO\n");}}return 0;}
对于一棵 个节点的有根树,给这棵树上的每个节点都涂上一种颜色,每次涂色可以选择一个节点,并将这个节点的子树(包括这个节点自身)全都涂上这种颜色,每个节点初始的颜色都是 ,要按照给定的涂色方式将这棵树涂上颜色,问最少需要涂多少次颜色。
第一行为一个整数 ,第二行为 个整数 ,第 个整数 代表第 个节点的父节点,第三行为 个整数 ,表示每个节点要涂上的颜色。
输出最少需要涂色的次数。
| 输入 | 输出 | 提示 |
|---|---|---|
| 6 1 2 2 1 5 2 1 1 1 1 1 |
3 | 给定的树如图:![]() 首先选择树根并将整棵树涂成颜色 ,如图: ![]() 接着可以选择节点 并将 的子树都涂成颜色 : ![]() 最后选择节点 并将对应的子树都涂成颜色 : ![]() |
| 7 1 1 2 3 1 4 3 3 1 1 1 2 3 |
5 |
贪心地从根节点开始涂色,按照 的顺序先涂根节点,再涂它的子树,只有出现子节点颜色和父节点颜色不同的时候才需要涂色,因此只要统计子节点颜色和父节点颜色不同的个数就是答案。
#include <iostream>#include <cstdio>#include <cstdlib>#include <cmath>#include <climits>#include <cfloat>#include <cstring>#include <string>#include <vector>#include <list>#include <queue>#include <stack>#include <map>#include <set>#include <algorithm>using namespace std;#define LL long longconst int maxn = 10000 + 100;int n, ans;int color[maxn], fa[maxn];int main() {#ifdef Dmaxiyafreopen("test.txt", "r", stdin);#endif // Dmaxiyaios::sync_with_stdio(false);while(scanf("%d", &n) != EOF) {ans = 0;for(int i = 2; i <= n; ++i) {scanf("%d", &fa[i]);}for(int i = 1; i <= n; ++i) {scanf("%d", &color[i]);if(color[i] != color[fa[i]]) {++ans;}}printf("%d\n", ans);}return 0;}
给定一个长度为 的序列 ,第 个数字 表示一棵树上第 层的节点数为 ,判断是否存在不同构的满足条件的两棵树。
第一行为一个整数 ,第二行为 个整数 ,数据保证至少有一种满足条件的树的结构,且 。
如果只有唯一一种满足条件的树的结构,则输出 ,否则在第一行输出 ,接下来两行每行 个数字,第 个数字表示第 个节点的父节点,如果这个节点为根节点,则它的父节点为 。
| 输入 | 输出 | 提示 |
|---|---|---|
| 2 1 1 1 |
perfect | 给定的序列只有唯一一种满足条件的树的结构:![]() |
| 2 1 2 2 |
ambiguous 0 1 1 3 3 0 1 1 3 2 |
给定的序列有两种满足条件的结构:![]() |
序列中只要存在两个连续的大于等于 的数字,就存在两种不同构的树满足条件,第一棵数每一层都以上一层的第一个节点为父节点,第二棵树只要在连续的两个 中第二个 对应的那一层,拿出一个节点作为上一层第二个节点的子节点,两棵树就不是同构的了。
#include <iostream>#include <cstdio>#include <cstdlib>#include <cmath>#include <climits>#include <cfloat>#include <cstring>#include <string>#include <vector>#include <list>#include <queue>#include <stack>#include <map>#include <set>#include <algorithm>using namespace std;#define LL long longconst int maxn = 200000 + 100;int h, cnt;int num[maxn];int main() {#ifdef Dmaxiyafreopen("test.txt", "r", stdin);#endif // Dmaxiyaios::sync_with_stdio(false);while(scanf("%d", &h) != EOF) {int Index = -1;cnt = 1;for(int i = 0; i <= h; ++i) {scanf("%d", &num[i]);}for(int i = 0; i < h; ++i) {if(num[i] >= 2 && num[i + 1] >= 2) {Index = i + 1;break;}}if(Index == -1) {printf("perfect\n");continue;}printf("ambiguous\n");int root = 0;int first = 0;for(int i = 0; i <= h; ++i) {root = first;first = cnt;for(int j = 0; j < num[i]; ++j) {if(i != 0) {printf(" ");}printf("%d", root);++cnt;}}printf("\n");cnt = 1;first = 0;for(int i = 0; i <= h; ++i) {root = first;first = cnt;for(int j = 0; j < num[i]; ++j) {if(i != 0) {printf(" ");}if(Index == i && j == 1) {printf("%d", root + 1);} else {printf("%d", root);}++cnt;}}printf("\n");}return 0;}