@Dmaxiya
2020-12-12T15:21:10.000000Z
字数 3701
阅读 1057
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 long
int n, m, a, b, ans;
int main() {
#ifdef Dmaxiya
freopen("test.txt", "r", stdin);
#endif // Dmaxiya
ios::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 long
const int maxn = 10000 + 100;
int n, ans;
int color[maxn], fa[maxn];
int main() {
#ifdef Dmaxiya
freopen("test.txt", "r", stdin);
#endif // Dmaxiya
ios::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 long
const int maxn = 200000 + 100;
int h, cnt;
int num[maxn];
int main() {
#ifdef Dmaxiya
freopen("test.txt", "r", stdin);
#endif // Dmaxiya
ios::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;
}