Problem:
Score : 1100 points

Problem Statement

There is a tree with N vertices, numbered 1 through N.
The i-th edge in this tree connects Vertices A_i and B_i and has a length of C_i.

Joisino created a complete graph with N vertices.
The length of the edge connecting Vertices u and v in this graph, is equal to the shortest distance between Vertices u and v in the tree above.

Joisino would like to know the length of the longest Hamiltonian path (see Notes) in this complete graph.
Find the length of that path.

Notes

A Hamiltonian path in a graph is a path in the graph that visits each vertex exactly once.

Constraints

2 \leq N \leq 10^5

1 \leq A_i < B_i \leq N

The given graph is a tree.

1 \leq C_i \leq 10^8

All input values are integers.

Input

Input is given from Standard Input in the following format:

N
A_1 B_1 C_1
A_2 B_2 C_2
:
A_{N-1} B_{N-1} C_{N-1}

Output

Print the length of the longest Hamiltonian path in the complete graph created by Joisino.

Sample Input 1

5
1 2 5
3 4 7
2 3 3
2 5 2

Sample Output 1

38

The length of the Hamiltonian path 5 → 3 → 1 → 4 → 2 is 5+8+15+10=38. Since there is no Hamiltonian path with length 39 or greater in the graph, the answer is 38.

Sample Input 2

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

Sample Output 2

132

Solution in C++14 (Clang 3.8.0) (judge verdict: Accepted)

#include <algorithm>
#include <iostream>
#include <iomanip>
#include <cstring>
#include <string>
#include <vector>
#include <random>
#include <bitset>
#include <queue>
#include <cmath>
#include <stack>
#include <set>
#include <map>
typedef long long ll;
using namespace std;
const ll MOD = 1000000007LL;

struct Edge {
    int to;
    ll cost;
};

vector<int> Centroid(const vector<vector<Edge>> &edge) {
    int n = edge.size();
    vector<int> centroids;
    vector<int> sz(n);
    function<void(int, int)> dfs = [&](int cur, int par) {
        sz[cur] = 1;
        bool is_centroid = true;
        for (Edge ch : edge[cur]) {
            if (ch.to == par) continue;
            dfs(ch.to, cur);
            sz[cur] += sz[ch.to];
            if (sz[ch.to] > n / 2) is_centroid = false;
        }
        if (n - sz[cur] > n / 2) is_centroid = false;
        if (is_centroid) centroids.push_back(cur);
    };
    dfs(0, -1);
    return centroids;
}

ll total_cost[100005];

void dfs(vector<vector<Edge>> &edge, int cur, int par, ll sum) {
    total_cost[cur] = sum;
    for (Edge e : edge[cur]) {
        if (e.to == par) continue;
        dfs(edge, e.to, cur, sum + e.cost);
    }
}

int main() {
    cin.sync_with_stdio(false);
    cin.tie(0);
    cout.tie(0);

    int n;
    cin >> n;

    vector<vector<Edge>> edge(n);
    for (int i = 1; i < n; i++) {
        int a, b;
        ll c;
        cin >> a >> b >> c;
        a--; b--;

        edge[a].push_back(Edge{b, c});
        edge[b].push_back(Edge{a, c});
    }

    vector <int> centroids = Centroid(edge);

    ll ans = 0;
    if (centroids.size() == 2) {
        for (Edge e : edge[centroids[0]]) {
            if (e.to == centroids[1]) {
                ans -= e.cost;
            }
        }
    } else {
        ll mn = 1LL << 30;
        for (Edge e : edge[centroids[0]]) {
            mn = min(mn, e.cost);
        }
        ans -= mn;
    }

    int center = centroids[0];
    dfs(edge, center, -1, 0);

    for (int i = 0; i < n; i++) {
        ans += 2LL * total_cost[i];
    }

    cout << ans << "\n";
    return 0;
}