Problem:
Score : 600 points

Problem Statement

We have a tree with N vertices, whose i-th edge connects Vertex u_i and Vertex v_i.
Vertex i has an integer a_i written on it.
For every integer k from 1 through N, solve the following problem:

We will make a sequence by lining up the integers written on the vertices along the shortest path from Vertex 1 to Vertex k, in the order they appear. Find the length of the longest increasing subsequence of this sequence.

Here, the longest increasing subsequence of a sequence A of length L is the subsequence A_{i_1} , A_{i_2} , ... , A_{i_M} with the greatest possible value of M such that 1 \leq i_1 < i_2 < ... < i_M \leq L and A_{i_1} < A_{i_2} < ... < A_{i_M}.

Constraints

2 \leq N \leq 2 \times 10^5

1 \leq a_i \leq 10^9

1 \leq u_i , v_i \leq N

u_i \neq v_i

The given graph is a tree.

All values in input are integers.

Input

Input is given from Standard Input in the following format:

N
a_1 a_2 ... a_N
u_1 v_1
u_2 v_2
:
u_{N-1} v_{N-1}

Output

Print N lines. The k-th line, print the length of the longest increasing subsequence of the sequence obtained from the shortest path from Vertex 1 to Vertex k.

Sample Input 1

10
1 2 5 3 4 6 7 3 2 4
1 2
2 3
3 4
4 5
3 6
6 7
1 8
8 9
9 10

Sample Output 1

1
2
3
3
4
4
5
2
2
3

For example, the sequence A obtained from the shortest path from Vertex 1 to Vertex 5 is 1,2,5,3,4. Its longest increasing subsequence is A_1, A_2, A_4, A_5, with the length of 4.

Solution in Rust (1.42.0) (judge verdict: Wrong Answer)

const MAX_N: usize = 200_010;
use std::collections::BTreeMap;
use std::ops::Bound::Included;

#[derive(Default)]
//NOTE
//declare variables to reduce the number of parameters for dp and dfs etc.
struct Solver {
    a: Vec<usize>,
    edges: Vec<Vec<usize>>,
    costs: BTreeMap<usize, (i32, i32)>,
    results: Vec<i32>,
}

impl Solver {
    fn dfs(&mut self, pos: usize, pre: Option<usize>) {
        for idx in 0..self.edges[pos].len() {
            let nxt = self.edges[pos][idx];
            if Some(nxt) == pre {
                continue;
            }
            let b = self.a[nxt];
            let p = self.costs.range(..b).next_back();
            //eprintln!("costs: {:?}", self.costs);
            //eprintln!("{} {} {:?}", nxt, b, p);
            //none
            let c = if let Some(p) = p {
                let c = (p.1).0;
                let cnt = if *p.0 == b {
                    assert!(false);
                    (p.1).1 + 1
                } else {
                    1
                };
                self.costs.insert(b, (c + 1, cnt));
                (c + 1, cnt)
            } else {
                self.costs.insert(b, (1, 1));
                (1, 1)
            };

            self.results[nxt] = c.0;
            self.dfs(nxt, Some(pos));

            if c.1 == 1 {
                self.costs.remove(&b);
            } else {
                self.costs.insert(b, (c.0 - 1, c.1 - 1));
            }
        }
    }
    fn solve(&mut self) {
        let stdin = std::io::stdin();
        let mut scn = Scanner {
            stdin: stdin.lock(),
        };
        let n: usize = scn.read();
        let a: Vec<usize> = scn.vec(n);

        let mut edges = vec![vec![]; MAX_N];
        let uv: Vec<_> = (0..n - 1)
            .map(|_| {
                let u: usize = scn.read();
                let v: usize = scn.read();
                edges[u - 1].push(v - 1);
                edges[v - 1].push(u - 1);
                (u - 1, v - 1)
            })
            .collect();

        self.a = a;
        self.edges = edges;
        self.results = vec![0; n];

        self.costs.insert(self.a[0], (1, 1));
        self.results[0] = 1;
        self.dfs(0, None);
        //eprintln!("{:?}", self.costs);

        for x in self.results.iter() {
            println!("{}", x);
        }
    }
}

fn main() {
    std::thread::Builder::new()
        .stack_size(64 * 1024 * 1024) // 64MB
        .spawn(|| {
            let mut solver = Solver::default();
            solver.solve()
        })
        .unwrap()
        .join()
        .unwrap();
}
pub mod utils {
    const DYX: [(isize, isize); 8] = [
        (0, 1),   //right
        (1, 0),   //down
        (0, -1),  //left
        (-1, 0),  //top
        (1, 1),   //down right
        (-1, 1),  //top right
        (1, -1),  //down left
        (-1, -1), //top left
    ];

    pub fn try_adj(y: usize, x: usize, dir: usize, h: usize, w: usize) -> Option<(usize, usize)> {
        let ny = y as isize + DYX[dir].0;
        let nx = x as isize + DYX[dir].1;
        if ny >= 0 && nx >= 0 {
            let ny = ny as usize;
            let nx = nx as usize;
            if ny < h && nx < w {
                Some((ny, nx))
            } else {
                None
            }
        } else {
            None
        }
    }
}

//snippet from kenkoooo
pub struct Scanner<R> {
    stdin: R,
}

impl<R: std::io::Read> Scanner<R> {
    pub fn read<T: std::str::FromStr>(&mut self) -> T {
        use std::io::Read;
        let buf = self
            .stdin
            .by_ref()
            .bytes()
            .map(|b| b.unwrap())
            .skip_while(|&b| b == b' ' || b == b'\n' || b == b'\r')
            .take_while(|&b| b != b' ' && b != b'\n' && b != b'\r')
            .collect::<Vec<_>>();
        unsafe { std::str::from_utf8_unchecked(&buf) }
            .parse()
            .ok()
            .expect("Parse error.")
    }
    pub fn read_line(&mut self) -> String {
        use std::io::Read;
        let buf = self
            .stdin
            .by_ref()
            .bytes()
            .map(|b| b.unwrap())
            .skip_while(|&b| b == b'\n' || b == b'\r')
            .take_while(|&b| b != b'\n' && b != b'\r')
            .collect::<Vec<_>>();
        unsafe { std::str::from_utf8_unchecked(&buf) }
            .parse()
            .ok()
            .expect("Parse error.")
    }
    pub fn vec<T: std::str::FromStr>(&mut self, n: usize) -> Vec<T> {
        (0..n).map(|_| self.read()).collect()
    }

    pub fn chars(&mut self) -> Vec<char> {
        self.read::<String>().chars().collect()
    }
}