Problem: Find the sum of weights of edges of the Minimum Spanning Tree for a given weighted undirected graph G = (V, E).

Constraints

* 1 ≤ |V| ≤ 10,000
* 0 ≤ |E| ≤ 100,000
* 0 ≤ wi ≤ 10,000
* The graph is connected
* There are no parallel edges
* There are no self-loops

Input


|V| |E|
s0 t0 w0
s1 t1 w1
:
s|E|-1 t|E|-1 w|E|-1


, where |V| is the number of vertices and |E| is the number of edges in the graph. The graph vertices are named with the numbers 0, 1,..., |V|-1 respectively.

si and ti represent source and target verticess of i-th edge (undirected) and wi represents the weight of the i-th edge.

Output

Print the sum of the weights of the Minimum Spanning Tree.

Examples

Input

4 6
0 1 2
1 2 1
2 3 1
3 0 1
0 2 3
1 3 5


Output

3


Input

6 9
0 1 1
0 2 3
1 2 1
1 3 7
2 4 1
1 4 3
3 4 1
3 5 1
4 5 6


Output

5

Solution (in JAVA):

Solution:
import java.util.*;
import java.io.*;

//http://judge.u-aizu.ac.jp/onlinejudge/review.jsp?rid=2027297#1
public class Main {

	static int vertex;
	static int edges;
	static boolean[] visited;
	static int[] cost;
	static int[] parent;
	static ArrayList<Edge>[] graph;
	static BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
	static final int INFINITY = Integer.MAX_VALUE;
	static Main obj = new Main();

	class Edge implements Comparable<Edge> {

		int from;
		int to;
		int weight;

		public Edge(int from, int to, int weight) {
			this.from = from;
			this.to = to;
			this.weight = weight;
		}

		@Override
		public int compareTo(Edge other) {
			int diff = weight - other.weight;
			return diff;
		}

	}

	public static void main(String[] args) throws IOException {

		input();
		prim();

	}

	@SuppressWarnings("unchecked")
	public static void input() throws IOException {
		StringTokenizer st = new StringTokenizer(br.readLine());
		vertex = Integer.parseInt(st.nextToken());
		edges = Integer.parseInt(st.nextToken());
		visited = new boolean[vertex];
		cost = new int[vertex];
		parent = new int[vertex];
		graph = new ArrayList[vertex];
		for (int i = 0; i < graph.length; i++) {
			graph[i] = new ArrayList<Edge>();
		}
		for (int i = 0; i < edges; i++) {
			st = new StringTokenizer(br.readLine());
			int a = Integer.parseInt(st.nextToken());
			int b = Integer.parseInt(st.nextToken());
			int c = Integer.parseInt(st.nextToken());

			graph[a].add(obj.new Edge(a, b, c));
			graph[b].add(obj.new Edge(b, a, c));

		}
		for (int i = 0; i < cost.length; i++) {
			cost[i] = INFINITY;
		}

	}

	public static void prim() {

		int added = 1;
		int sum = 0;
		visited[0] = true;
		cost[0] = 0;
		PriorityQueue<Edge> pq = new PriorityQueue<Edge>();
		for (Edge e : graph[0]) {
			pq.offer(e);
		}
		while (!pq.isEmpty()) {
			Edge e = pq.poll();
			if (visited[e.to]) {
				continue;
			}

			sum += e.weight;
			added++;
			cost[e.to] = e.weight;
			parent[e.to] = e.from;
			visited[e.to] = true;

			if (added == vertex) {
				break;
			}
			for (Edge q : graph[e.to]) {
				if (visited[q.to]) {
					continue;
				} else {
					pq.offer(q);
				}
			}

		}
		System.out.println(sum);

	}

}