#include <bits/stdc++.h>
using namespace std;
using Int = long long;
using Graph = vector<vector<int>>;
const Int INF = 1e18;
Graph G;
vector<int> A;
vector<Int> B;
vector<vector<Int>> C;
Int neg(const vector<Int> &A) {
    for (int i = 0; i < A.size(); i++) {
        if (A[i] < 0) return i;
    }
    return INF;
}
vector<Int> f(const vector<Int> &A, const vector<Int> &B) {
    vector<Int> ans(A.size() + B.size() - 1, INF);
    for (int i = 0; i < A.size(); i++) {
        for (int j = 0; j < B.size(); j++) {
            ans[i + j] = min(ans[i + j], A[i] + B[j]);
        }
    }
    return ans;
}
void recur(int node, int prev) {
    for (auto next : G[node]) if (next != prev) {
        recur(next, node);
    }
    if (A[node] > 0) {
        B[node] = 0;
        for (auto next : G[node]) if (next != prev) {
            if (A[next] > 0) {
                B[node] += min(neg(C[next]) + 1, B[next]);
            } else {
                B[node] += neg(C[next]) + 1;
            }
        }
    }
    vector<Int> X = {A[node]};
    for (auto next : G[node]) if (next != prev) {
        X = f(X, C[next]);
    }
    if (A[node] > 0) {
        X.resize(max((Int)X.size(), B[node] + 1 + 1), INF);
        X[B[node] + 1] = min(X[B[node] + 1], 0LL);
    }
    C[node] = X;
}
int main() {
    int N; cin >> N;
    G.resize(N);
    A.resize(N); for (auto &a : A) cin >> a;
    B.resize(N, INF);
    C.resize(N);
    for (int i = 0; i < N - 1; i++) {
        int u, v; cin >> u >> v; u--, v--;
        G[u].push_back(v);
        G[v].push_back(u);
    }
    recur(0, -1);
    cout << min(B[0], neg(C[0])) << '\n';
    return 0;
}
