#include <bits/stdc++.h>

using namespace std;

#define DEBUG(x) cerr<<#x<<": "<<x<<endl;
#define DEBUG_VEC(v) cerr<<#v<<":";for(int i=0;i<v.size();i++) cerr<<" "<<v[i]; cerr<<endl

typedef long long ll;
#define vi vector<int>
#define vl vector<ll>
#define vii vector< vector<int> >
#define vll vector< vector<ll> >
#define vs vector<string>
#define pii pair<int,int>
#define pis pair<int,string>
#define psi pair<string,int>
#define pll pair<ll,ll>
template<class S, class T> pair<S, T> operator+(const pair<S, T> &s, const pair<S, T> &t) { return pair<S, T>(s.first + t.first, s.second + t.second); }
template<class S, class T> pair<S, T> operator-(const pair<S, T> &s, const pair<S, T> &t) { return pair<S, T>(s.first - t.first, s.second - t.second); }
template<class S, class T> ostream& operator<<(ostream& os, pair<S, T> p) { os << "(" << p.first << ", " << p.second << ")"; return os; }
#define X first
#define Y second
#define rep(i,n) for(int i=0;i<(n);i++)
#define rep1(i,n) for(int i=1;i<=(n);i++)
#define rrep(i,n) for(int i=(n)-1;i>=0;i--)
#define rrep1(i,n) for(int i=(n);i>0;i--)
#define REP(i,a,b) for(int i=a;i<b;i++)
#define in(x, a, b) (a <= x && x < b)
#define all(c) c.begin(),c.end()
template<class T> bool chmax(T &a, const T &b) { if (a<b) { a = b; return 1; } return 0; }
template<class T> bool chmin(T &a, const T &b) { if (a>b) { a = b; return 1; } return 0; }
#define UNIQUE(v) v.erase(std::unique(v.begin(), v.end()), v.end());
const ll inf = 1000000001;
const ll INF = 1e18;
const ll MOD = 1000000007;
//const ll MOD = 998244353;
const double pi = 3.14159265358979323846;
#define Sp(p) cout<<setprecision(15)<< fixed<<p<<endl;
int dx[4] = { 1,0, -1,0 }, dy[4] = { 0,1,0,-1 };
int dx2[8] = { 1,1,0,-1,-1,-1,0,1 }, dy2[8] = { 0,1,1,1,0,-1,-1,-1 };
#define fio() cin.tie(0); ios::sync_with_stdio(false);
//#define mp make_pair


class UnionFind {
public:
	int n;
	vi par; //親
	vi ran; //木の深さ
	vi num; //要素数

	UnionFind(int _n) {
		n = _n;
		par.resize(n); ran.resize(n); num.resize(n);
		for (int i = 0; i < n; i++) {
			par[i] = i; ran[i] = 0; num[i] = 1;
		}
	}

	//木の根を求める
	int find(int x) {
		if (par[x] == x) {
			return x;
		}
		else {
			return par[x] = find(par[x]);
		}
	}

	//xとyの属する集合を併合
	void unite(int x, int y) {
		x = find(x); y = find(y);
		int numsum = num[x] + num[y];
		if (x == y) {
			return;
		}
		if (ran[x]<ran[y]) {
			par[x] = y;
		}
		else {
			par[y] = x;
			if (ran[x] == ran[y]) {
				ran[x]++;
			}
		}
		num[x] = num[y] = numsum;
	}

	//xとyが同じ集合に属するか否か
	bool same(int x, int y) {
		return find(x) == find(y);
	}

};


vl x(200010);
vector<pair<ll, pii> > edges;

ll kruskal(int n) {
	sort(edges.begin(), edges.end());
	UnionFind uf(n);
	ll res = 0;
	for (int i = 0; i < edges.size(); i++) {
		if (!uf.same(edges[i].second.first, edges[i].second.second)) {
			uf.unite(edges[i].second.first, edges[i].second.second);
			res += edges[i].first;
		}
	}
	return res;
}

#define pli pair<ll, int>
#define pil pair<int, ll>
set<pii> st;

class CentroidDecomposition {
public:
  int n; //頂点数
  vector<vector<pil> >  G; //グラフの隣接リスト表現
  vector<bool> isused; //その頂点がすでに分割に使われているか
  vi subtreesize; //部分木のサイズ,更新される
  vi parent;
  vi centroid; //重心が後ろに追加されていく
  
  CentroidDecomposition(int n) : n(n) {
    G.resize(n); isused.resize(n);
    subtreesize.resize(n); parent.resize(n);
  }

  void add_edge(int u, int v, ll c) {
    G[u].push_back(pil(v, c)); G[v].push_back(pil(u, c));
  }

  int search_centroid(int now, int par, int size) {
    subtreesize[now] = 1;
    parent[now] = par;
    bool iscentroid = true;
    for (int i = 0; i < G[now].size(); i++) {
      int child = G[now][i].first;
      if (child == par) continue;
      if (isused[child]) continue;
      int child_size = search_centroid(child, now, size);
      if (child_size > size / 2) iscentroid = false;
      subtreesize[now] += child_size;
    }
    if (size - subtreesize[now] > size / 2) {
      iscentroid = false;
    }
    if (iscentroid) {
      centroid.push_back(now);
    }
    return subtreesize[now];
  }

  pli dfs(int now, int par, ll d) {
    pli res = {x[now] + d, now};
    rep (i, G[now].size()) {
      int ch = G[now][i].first;
      if (ch == par) continue;
      if (isused[ch]) continue;
      res = min(res, dfs(ch, now, d + G[now][i].second));
    }
    return res;
  }

  void dfs2(int now, int par, ll d, int cent, vector<pair<pli, int> >& two, int i2) {
    pli temp = {x[now] + d, now};
    rep (i, two.size()) {
      if (two[i].second != i2) {
        int u = two[i].first.second;
        ll d2 = two[i].first.first;
        edges.push_back({d2 + temp.first, pii(now, u)});
        break;
      }
    }
    edges.push_back({x[now] + d + x[cent], pii(now, cent)});
    rep (i, G[now].size()) {
      int ch = G[now][i].first;
      if (ch == par) continue;
      if (isused[ch]) continue;
      dfs2(ch, now, d + G[now][i].second, cent, two, i2);
    }
  }
  
  //問題によって変わる
  void solve(int root, int size) {
    search_centroid(root, -1, size);
    int cent = centroid.back();
    isused[cent] = true;
    vector<pair<pli, int> > two;
    rep(i, G[cent].size()) {
      int ch = G[cent][i].first;
      if (isused[ch]) {
        continue;
      }
      pli temp = dfs(ch, cent, G[cent][i].second);
      auto temp2 = make_pair(temp, i);
      if (two.size() == 0) two.push_back({temp, i});
      else if (two.size() == 1) {
        if (two[0].first < temp) two.push_back({temp, i});
        else two.insert(two.begin(), {temp, i});
      }
      else {
        if (two[0].first > temp) {
          two.pop_back();
          two.insert(two.begin(), {temp, i});
        }
        else if (two[1].first > temp) {
          two.pop_back();
          two.push_back({temp, i});
        }
      }
    }
    rep (i, G[cent].size()) {
      int ch = G[cent][i].first;
      if (isused[ch]) {
        continue;
      }
      dfs2(ch, cent, G[cent][i].second, cent, two, i);
    }
    rep (i, G[cent].size()) {
      int ch = G[cent][i].first;
      if (isused[ch]) {
        continue;
      }
      if (parent[ch] == cent) {
        solve(ch, subtreesize[ch]);
      }
      else {
        solve(ch, size - subtreesize[cent]);
      }
    }
    return;
  }
};

int main() {
  int n;
  cin >> n;
  rep (i, n) {
    cin >> x[i];
  }
  CentroidDecomposition tree(n);
  rep (i, n - 1) {
    ll u, v, c;
    cin >> u >> v >> c;
    u--; v--;
    tree.add_edge(u, v, c);
    edges.push_back({c + x[u] + x[v], pii(u, v)});
  }
  tree.solve(0, n);
  sort(all(edges));
  //DEBUG_VEC(edges);
  cout << kruskal(n) << endl;
}


Measured memory_bytes: 160220