結果
| 問題 |
No.363 門松サイクル
|
| コンテスト | |
| ユーザー |
FF256grhy
|
| 提出日時 | 2016-04-19 15:24:25 |
| 言語 | C++11(廃止可能性あり) (gcc 13.3.0) |
| 結果 |
AC
|
| 実行時間 | 171 ms / 4,000 ms |
| コード長 | 3,074 bytes |
| コンパイル時間 | 188 ms |
| コンパイル使用メモリ | 26,344 KB |
| 実行使用メモリ | 20,280 KB |
| 最終ジャッジ日時 | 2024-10-04 14:06:45 |
| 合計ジャッジ時間 | 3,943 ms |
|
ジャッジサーバーID (参考情報) |
judge5 / judge4 |
(要ログイン)
| ファイルパターン | 結果 |
|---|---|
| sample | AC * 2 |
| other | AC * 27 |
コンパイルメッセージ
main.cpp: In function ‘int main()’:
main.cpp:63:14: warning: ignoring return value of ‘int scanf(const char*, ...)’ declared with attribute ‘warn_unused_result’ [-Wunused-result]
63 | scanf("%d", &n);
| ~~~~~^~~~~~~~~~
main.cpp:64:39: warning: ignoring return value of ‘int scanf(const char*, ...)’ declared with attribute ‘warn_unused_result’ [-Wunused-result]
64 | for(i = 0; i < n; i++) { scanf("%d", &a[i]); }
| ~~~~~^~~~~~~~~~~~~
main.cpp:65:43: warning: ignoring return value of ‘int scanf(const char*, ...)’ declared with attribute ‘warn_unused_result’ [-Wunused-result]
65 | for(i = 0; i < n - 1; i++) { scanf("%d%d", &x[i], &y[i]); x[i]--; y[i]--; }
| ~~~~~^~~~~~~~~~~~~~~~~~~~~~
main.cpp:66:14: warning: ignoring return value of ‘int scanf(const char*, ...)’ declared with attribute ‘warn_unused_result’ [-Wunused-result]
66 | scanf("%d", &q);
| ~~~~~^~~~~~~~~~
main.cpp:67:43: warning: ignoring return value of ‘int scanf(const char*, ...)’ declared with attribute ‘warn_unused_result’ [-Wunused-result]
67 | for(i = 0; i < q ; i++) { scanf("%d%d", &u[i], &v[i]); u[i]--; v[i]--; }
| ~~~~~^~~~~~~~~~~~~~~~~~~~~~
ソースコード
#include <stdio.h>
int isK(int a, int b, int c) {
return ( (a < b && b > c && a != c) || (a > b && b < c && a != c) );
}
#define MAX 100000
#define NIL 0
#define ROOT 0
int n, a[MAX], x[MAX], y[MAX], q, u[MAX], v[MAX];
int first[MAX], last[MAX], list_val[MAX * 2 + 1], list_next[MAX * 2 + 1], ptr = 1;
int queue_val[MAX], get, set;
int height[MAX], ancestor[MAX][17], is_kado[MAX][17], flag[MAX];
// ancestor は 2^n 上のノード, is_kado は 2^n + 1 までが門松列かどうか
void add(int xx, int yy) {
if(first[xx] == NIL) {
first[xx] = ptr;
} else {
list_next[ last[xx] ] = ptr;
}
last[xx] = ptr;
list_val[ptr] = yy;
list_next[ptr] = NIL;
ptr++;
}
int up(int s, int n) {
int i = 0;
while(n) {
if(n % 2) { s = ancestor[s][i]; }
n /= 2;
i++;
}
return s;
}
int len(int n) {
int i = 0;
while(n) {
n /= 2;
i++;
}
return i;
}
int is_kado_func(int s, int t) {
// s から tの次 まで
int n = height[s] - height[t];
int i, ans = 1;
for(i = 0; i < len(n); i++) {
if(n & (1 << i)) {
ans &= is_kado[s][i];
s = ancestor[s][i];
}
}
return ans;
}
int main() {
int i, j;
scanf("%d", &n);
for(i = 0; i < n; i++) { scanf("%d", &a[i]); }
for(i = 0; i < n - 1; i++) { scanf("%d%d", &x[i], &y[i]); x[i]--; y[i]--; }
scanf("%d", &q);
for(i = 0; i < q ; i++) { scanf("%d%d", &u[i], &v[i]); u[i]--; v[i]--; }
for(i = 0; i < n - 1; i++) {
add(x[i], y[i]);
add(y[i], x[i]);
}
queue_val[set] = ROOT; set++;
flag[ROOT] = 1;
height[ROOT] = 0;
while(get != set) {
int qv = queue_val[get];
int p = first[qv];
while(p != NIL) {
int lv = list_val[p];
if(! flag[lv]) {
flag[lv] = 1;
queue_val[set] = lv; set++;
height[lv] = height[qv] + 1;
ancestor[lv][0] = qv;
for(i = 0; i < len(height[lv]) - 1; i++) {
ancestor[lv][i + 1] = ancestor[ ancestor[lv][i] ][i];
}
if(height[lv] >= 2) {
is_kado[lv][0] = isK( a[lv], a[ ancestor[lv][0] ], a[ ancestor[lv][1] ] );
for(i = 0; i < len(height[lv] - 1) - 1; i++) {
is_kado[lv][i + 1] = is_kado[lv][i] && is_kado[ ancestor[lv][i] ][i];
}
}
}
p = list_next[p];
}
get++;
}
for(i = 0; i < q; i++) {
if(height[ u[i] ] < height[ v[i] ]) {
int temp = u[i];
u[i] = v[i];
v[i] = temp;
}
int diff = height[ u[i] ] - height[ v[i] ];
int s = up(u[i], diff);
int t = v[i];
int ans;
if(s != t) {
for(j = len(height[s]) - 1; 0 <= j; j--) {
if(ancestor[s][j] != ancestor[t][j]) {
s = ancestor[s][j];
t = ancestor[t][j];
}
}
int c = ancestor[s][0];
int uu = ancestor[ u[i] ][0];
int vv = ancestor[ v[i] ][0];
ans = (
isK(a[s], a[c], a[t]) &&
isK(a[uu], a[u[i]], a[v[i]]) &&
isK(a[vv], a[v[i]], a[u[i]]) &&
is_kado_func(u[i], s) &&
is_kado_func(v[i], t)
);
} else {
int uu = ancestor[ u[i] ][0];
int vv = up(u[i], diff - 1);
ans = (
isK(a[uu], a[u[i]], a[v[i]]) &&
isK(a[vv], a[v[i]], a[u[i]]) &&
is_kado_func(u[i], vv)
);
}
printf("%s\n", ans ? "YES" : "NO");
}
return 0;
}
FF256grhy