#include <stdio.h>
#include <set>
#include <vector>
#include <algorithm>
using namespace std;
#define MAX_N 200010
#define mp make_pair
int n, m, sol, p2, k;
int anc[MAX_N], use[MAX_N], cost[MAX_N], c[MAX_N], niv[MAX_N];
int tata[20][MAX_N];
int tata2[MAX_N], next[MAX_N], d[MAX_N];
typedef set <pair <int, int> > MYSET;
MYSET s;
vector <int> G[MAX_N], vine[MAX_N], tree[MAX_N];
inline int get_father(int x, int niv) {
for (int i = p2; i >= 0; i--)
if ((1 << i) <= niv) {
x = tata[i][x];
niv -= 1 << i;
}
return x;
}
void build_tree(int init, int nod, int start, int stop) {
if (start > stop)
return;
int fiu = vine[init][start];
if (niv[fiu] > niv[nod] && get_father(fiu, niv[fiu] - niv[nod]) == nod) {
tree[nod].push_back(fiu);
tata2[fiu] = nod;
build_tree(init, fiu, start + 1, stop);
}
else
build_tree(init, tata2[nod], start, stop);
}
int dfs2(int nod) {
int len = tree[nod].size() - 1;
if (len >= 0) {
for (int i = len - 1; i >= 0; i--)
next[tree[nod][i]] = tree[nod][i + 1];
next[tree[nod][len]] = next[nod];
}
int ans = d[nod];
d[next[nod]] = max(d[next[nod]], d[nod] + c[nod]);
ans = max(ans, d[next[nod]]);
for (int i = 0; i <= len; i++) {
dfs2(tree[nod][i]);
ans = max(ans, d[tree[nod][i]]);
}
return ans;
}
void dfs(int nod) {
use[nod] = 1;
for (int i = 1; i <= p2; i++)
tata[i][nod] = tata[i - 1][tata[i - 1][nod]];
MYSET::iterator it = s.upper_bound(make_pair(cost[nod], nod)); //gasesc primul cost > costul curent
if (it != s.end())
anc[nod] = it->second;
s.insert(mp(cost[nod], nod));
if (anc[nod])
vine[anc[nod]].push_back(nod);
for (vector <int>::iterator Git = G[nod].begin(); Git != G[nod].end(); ++Git)
if (use[*Git] == 0) {
niv[*Git] = niv[nod] + 1;
tata[0][*Git] = nod;
dfs(*Git);
}
it = s.find(make_pair(cost[nod], nod));
s.erase(it);
int len = vine[nod].size() - 1;
for (int i = 0; i <= len; i++) {
vector <int> ().swap(tree[vine[nod][i]]);
tata2[vine[nod][i]] = d[vine[nod][i]] = 0;
}
build_tree(nod, nod, 0, vine[nod].size() - 1); //construiesc arborele micut
next[nod] = n + 1;
c[nod] = dfs2(nod) + 1;
sol = max(sol, c[nod]);
}
int main() {
freopen("guvern.in", "r", stdin);
freopen("guvern.out", "w", stdout);
scanf("%d", &n);
for (int i = 1; i < n; i++) {
int x, y;
scanf("%d %d", &x, &y);
G[x].push_back(y);
G[y].push_back(x);
}
for (int i = 1; i <= n; i++)
scanf("%d", &cost[i]);
for (int i = 0;; i++)
if ((1 << i) >= n) {
p2 = i;
break;
}
cost[0] = -2000000000; niv[1] = 1;
dfs(1);
printf("%d\n", sol);
return 0;
}