You are given a rooted tree with root in vertex 1. Each vertex is coloured in some colour.

Let's call colour c dominating in the subtree of vertex v if there are no other colours that appear in the subtree of vertex v more times than colour c. So it's possible that two or more colours will be dominating in the subtree of some vertex.

The subtree of vertex v is the vertex v and all other vertices that contains vertex v in each path to the root.

For each vertex v find the sum of all dominating colours in the subtree of vertex v.

Input

The first line contains integer n (1 ≤ n ≤ 105) — the number of vertices in the tree.

The second line contains n integers ci (1 ≤ ci ≤ n), ci — the colour of the i-th vertex.

Each of the next n - 1 lines contains two integers xj, yj (1 ≤ xj, yj ≤ n) — the edge of the tree. The first vertex is the root of the tree.

Output

Print n integers — the sums of dominating colours for each vertex.

Examples

Input

4
1 2 3 4
1 2
2 3
2 4


Output

10 9 3 4


Input

15
1 2 3 1 2 3 3 1 1 3 2 2 1 2 3
1 2
1 3
1 4
1 14
1 15
2 5
2 6
2 7
3 8
3 9
3 10
4 11
4 12
4 13


Output

6 5 4 3 2 3 3 1 1 3 2 2 1 2 3
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.io.OutputStreamWriter;
import java.io.PrintWriter;
import java.io.StreamTokenizer;
import java.util.Arrays;

public class Main {

	static ChainForwardStar tree;
	static int[] numNodes, heavy, color, count;
	static long[] result;
	static long sum;
	static int max;
	
	public static void main(String[] args) throws IOException {
		StreamTokenizer st = new StreamTokenizer(new BufferedReader(new InputStreamReader(System.in)));
		PrintWriter pw = new PrintWriter(new OutputStreamWriter(System.out));
		st.nextToken();
		int n = (int) st.nval;
		int[] color = new int[n];
		for (int i = 0; i != n; ++i) {
			st.nextToken();
			color[i] = (int) st.nval;
		}
		int e = n - 1;
		ChainForwardStar tree = new ChainForwardStar(n, e << 1);
		for (int i = 0; i != e; ++i) {
			st.nextToken();
			int s = (int) st.nval - 1;
			st.nextToken();
			int t = (int) st.nval - 1;
			tree.addEdge(s, t);
			tree.addEdge(t, s);
		}
		traverse(tree, 0, color);
		pw.print(result[0]);
		for (int i = 1; i != n; ++i)
			pw.print(" " + result[i]);
		pw.flush();
	}

	public static long[] traverse(ChainForwardStar tree, int root, int[] color) {
		Main.tree = tree;
		Main.color = color;
		int n = tree.v();
		numNodes = new int[n];
		Arrays.fill(numNodes, 1);
		heavy = new int[n];
		count = new int[n + 1];
		result = new long[n];
		dfs(root, -1);
		dfs2(root, -1, false);
		return result;
	}

	public static void dfs(int node, int parent) {
		int max = 0;
		for (int e = tree.first(node); e != -1; e = tree.next(e)) {
			int child = tree.to(e);
			if (child != parent) {
				dfs(child, node);
				numNodes[node] += numNodes[child];
				if (max < numNodes[child]) {
					max = numNodes[child];
					heavy[node] = child;
				}
			}
		}
	}

	public static void update(int node, int value) {
		count[color[node]] += value;
		if (count[color[node]] > max) {
			max = count[color[node]];
			sum = color[node];
		} else if (count[color[node]] == max)
			sum += color[node];
	}

	public static void updateAll(int node, int parent, int value) {
		update(node, value);
		for (int e = tree.first(node); e != -1; e = tree.next(e)) {
			int child = tree.to(e);
			if (child != parent)
				updateAll(child, node, value);
		}
	}

	public static void aggregate(int node, int parent) {
		for (int e = tree.first(node); e != -1; e = tree.next(e)) {
			int child = tree.to(e);
			if (child != parent && child != heavy[node])
				updateAll(child, node, 1);
		}
		update(node, 1);
	}

	public static void substract(int node, int parent) {
		for (int e = tree.first(node); e != -1; e = tree.next(e)) {
			int child = tree.to(e);
			if (child != parent)
				updateAll(child, node, -1);
		}
		update(node, -1);
	}

	public static void dfs2(int node, int parent, boolean isHeavy) {
		for (int e = tree.first(node); e != -1; e = tree.next(e)) {
			int child = tree.to(e);
			if (child != parent && child != heavy[node])
				dfs2(child, node, false);
		}
		if (numNodes[node] != 1)
			dfs2(heavy[node], node, true);
		aggregate(node, parent);
		result[node] = sum;
		if (!isHeavy) {
			substract(node, parent);
			sum = max = 0;
		}
	}
}

class ChainForwardStar {

	final int[] head;
	final int[] next;
	final int[] to;
	int size;

	public ChainForwardStar(int v, int e) {
		size = 0;
		head = new int[v];
		next = new int[e];
		Arrays.fill(head, -1);
		to = new int[e];
	}

	public void addEdge(int s, int t) {
		to[size] = t;
		next[size] = head[s];
		head[s] = size++;
	}

	public int to(int e) {
		return to[e];
	}

	public int first(int v) {
		return head[v];
	}

	public int next(int e) {
		return next[e];
	}

	public int v() {
		return head.length;
	}

	public int e() {
		return next.length;
	}
}