<|instruction|>
Solve the below problem. The solution should start with an abridged problem statement. Then key observations. Then full solution based on the observations. Then C++ and Python implementations with comments.

149. Computer Network
time limit per test: 0.25 sec.
memory limit per test: 4096 KB
input: standard input
output: standard output



A school bought the first computer some time ago. During the recent years the school bought N-1 new computers. Each new computer was connected to one of settled earlier. Managers of school are anxious about slow functioning of the net and want to know for each computer number Si - maximum distance, for which i-th computer needs to send signal (i.e. length of cable to the most distant computer). You need to provide this information.

Input
There is natural number N (N<=10000) in the first line of input, followed by (N-1) lines with descriptions of computers. i-th line contains two natural numbers - number of computer, to which i-th computer is connected and length of cable used for connection. Total length of cable does not exceed 10^9. Numbers in lines of input are separated by a space.

Output
Write N lines in output file. i-th line must contain number Si for i-th computer (1<=i<=N).

Sample test(s)

Input
3
1 1
1 2

Output
2
3
3
Author:	Andrew V. Lazarev, Michael R. Mirzayanov
Resource:	Saratov Subregional School Team Contest, 2002
Date:	Fall, 2002

<|response|>
1. Abridged problem statement  
You are given a tree of N computers (numbered 1 through N). Computer 1 is the root, and each computer i (2 ≤ i ≤ N) is connected to exactly one earlier computer by a cable of given length. For each computer i, compute Si, the maximum total cable length on a path from i to any other computer in the network.

2. Key observations  
- The network is a weighted tree, so there is exactly one simple path between any two nodes.  
- The “eccentricity” of a node is the greatest distance from that node to any other node in the tree.  
- In a tree, all farthest distances from an arbitrary node lie on the tree’s diameter (the longest path between any two nodes).  
- If U and V are the two ends of the diameter, then for every node i, its eccentricity is max(distance(i, U), distance(i, V)).  

3. Full solution approach  
a. Build an undirected weighted adjacency list of the tree.  
b. Run a DFS (or BFS) from node 1 (or any arbitrary node) to compute distances dist0[]. Find the farthest node U from 1.  
c. Run a second DFS from U to compute distU[], and identify the farthest node V from U. The path U–V is a diameter.  
d. Run a third DFS from V to compute distV[].  
e. For each node i, the answer Si = max(distU[i], distV[i]).  
All three DFS traversals take O(N) time, which is efficient for N up to 10 000.

4. C++ implementation with detailed comments  
```cpp
#include <bits/stdc++.h>
using namespace std;

int N;
// adj[u] holds pairs (v, w) meaning an edge u–v of weight w
vector<vector<pair<int,int>>> adj;

// Read input and build the tree
void read_input() {
    ios::sync_with_stdio(false);
    cin.tie(nullptr);

    cin >> N;
    adj.assign(N, {});
    // For i = 1..N-1, read its parent u and cable length w
    for(int i = 1; i < N; i++) {
        int u, w;
        cin >> u >> w;
        u--; // convert to 0-based index
        adj[i].push_back({u, w});
        adj[u].push_back({i, w});
    }
}

// Perform DFS from source 'src' to compute distance[] array
vector<long long> compute_distances(int src) {
    vector<long long> dist(N, -1);
    dist[src] = 0;
    // recursive lambda for DFS
    function<void(int,int)> dfs = [&](int u, int parent) {
        for(auto &edge : adj[u]) {
            int v = edge.first;
            int w = edge.second;
            if(v == parent) continue;
            dist[v] = dist[u] + w;
            dfs(v, u);
        }
    };
    dfs(src, -1);
    return dist;
}

int main() {
    read_input();

    // 1) DFS from node 0 to find one endpoint U of the diameter
    vector<long long> dist0 = compute_distances(0);
    int U = max_element(dist0.begin(), dist0.end()) - dist0.begin();

    // 2) DFS from U to get distU[] and find the other endpoint V
    vector<long long> distU = compute_distances(U);
    int V = max_element(distU.begin(), distU.end()) - distU.begin();

    // 3) DFS from V to get distV[]
    vector<long long> distV = compute_distances(V);

    // 4) For each node i, its eccentricity is max(distU[i], distV[i])
    for(int i = 0; i < N; i++) {
        cout << max(distU[i], distV[i]) << "\n";
    }
    return 0;
}
```

5. Python implementation with detailed comments  
```python
import sys
sys.setrecursionlimit(20000)

def read_tree():
    data = sys.stdin.read().split()
    it = iter(data)
    n = int(next(it))
    # adjacency list: for each node, list of (neighbor, weight)
    adj = [[] for _ in range(n)]
    for i in range(1, n):
        u = int(next(it)) - 1
        w = int(next(it))
        adj[i].append((u, w))
        adj[u].append((i, w))
    return n, adj

def dfs_distances(adj, src):
    n = len(adj)
    dist = [-1] * n
    dist[src] = 0
    # recursive DFS to fill dist[]
    def dfs(u, parent):
        for v, w in adj[u]:
            if v == parent:
                continue
            dist[v] = dist[u] + w
            dfs(v, u)
    dfs(src, -1)
    return dist

def main():
    n, adj = read_tree()
    # 1) DFS from node 0
    dist0 = dfs_distances(adj, 0)
    # find farthest node U
    U = max(range(n), key=lambda i: dist0[i])
    # 2) DFS from U
    distU = dfs_distances(adj, U)
    V = max(range(n), key=lambda i: distU[i])
    # 3) DFS from V
    distV = dfs_distances(adj, V)
    # 4) output max(distU[i], distV[i]) for each i
    out = [str(max(distU[i], distV[i])) for i in range(n)]
    print("\n".join(out))

if __name__ == "__main__":
    main()
```