//! Solves [Water Tree](http://codeforces.com/contest/343/problem/D). //! To make a self-contained file for contest submission, dump each desired //! module's contents directly here instead of the use statements. //! Also, use the commented code in main() to employ standard I/O. extern crate contest_algorithms; use contest_algorithms::graph::Graph; use contest_algorithms::range_query::{specs::AssignSum, StaticArq}; use contest_algorithms::scanner::Scanner; use std::io; const SAMPLE_INPUT: &[u8] = b"\ 5 1 2 5 1 2 3 4 2 12 1 1 2 3 3 1 3 2 3 3 3 4 1 2 2 4 3 1 3 3 3 4 3 5 "; const SAMPLE_OUTPUT: &[u8] = b"\ 0 0 0 1 0 1 0 1 "; fn dfs( graph: &Graph, u: usize, l: &mut [usize], r: &mut [usize], p: &mut [usize], time: &mut usize, ) { *time += 1; l[u] = *time; for (_, v) in graph.adj_list(u) { if l[v] == 0 { p[v] = l[u]; dfs(graph, v, l, r, p, time); } } r[u] = *time; } fn solve(scan: &mut Scanner, out: &mut W) { let n = scan.token::(); let mut tree = Graph::new(n, 2 * (n - 1)); for _ in 1..n { let u = scan.token::() - 1; let v = scan.token::() - 1; tree.add_undirected_edge(u, v); } let mut l = vec![0; n]; let mut r = vec![0; n]; let mut p = vec![0; n]; dfs(&tree, 0, &mut l, &mut r, &mut p, &mut 0); let mut arq = StaticArq::::new(&vec![0; n + 1]); let q = scan.token::(); for _ in 0..q { let c = scan.token::(); let v = scan.token::() - 1; let len = (r[v] - l[v] + 1) as i64; let sum = arq.query(l[v], r[v]); if c == 1 { if sum != len { arq.update(p[v], p[v], &0); arq.update(l[v], r[v], &1); } } else if c == 2 { arq.update(l[v], l[v], &0); } else { let ans = if sum == len { 1 } else { 0 }; writeln!(out, "{}", ans).ok(); } } } #[test] fn main() { let mut scan = Scanner::new(SAMPLE_INPUT); let mut out = vec![]; solve(&mut scan, &mut out); assert_eq!(out, SAMPLE_OUTPUT); }