Go: package main

import (
	"strconv"
	"fmt"
	"bufio"
	"os"
)
const INF = 1 << 21
var scanner = bufio.NewScanner(os.Stdin)

func nextInt() int {
	scanner.Scan()
	i, e := strconv.Atoi(scanner.Text())
	if e != nil {
		panic(e)
	}
	return i
}


func main() {
	scanner.Split(bufio.ScanWords)
	n := nextInt()
	adj := make([][]int, n)
	for i := range adj {
		adj[i] = make([]int, n)
	}

	for i := 0;i < n; i++ {
		u := nextInt()
		k := nextInt()
		for j := 0; j < k; j++ {
			v := nextInt()
			c := nextInt()
			adj[u][v] = c
		}
	}

	// for i := range adj {
	// 	fmt.Println(adj[i])
	// }

	dist := make([]int, n)
	prev := make([]int, n)
	visited := make([]bool, n)
	dijkstra := func(start int, size int) {
		for i := 0; i < size; i++ {
			dist[i] = INF
			prev[i] = -1
			visited[i] = false
		}
		dist[start] = 0
		for {
			u := -1
			tmp_min := INF
			for i := 0; i < size; i++ {
				if visited[i] == false && dist[i] < tmp_min {
					tmp_min = dist[i]
					u = i
				}
			}
			if u == -1 {
				break
			}
			visited[u] = true
			for i := 0; i < size; i++ {
				if adj[u][i] > 0 {
					w := adj[u][i]
					newlen := dist[u] + w
					if newlen < dist[i] {
						dist[i] = newlen
						prev[i] = u
					}
				}
			}
		}
	}
	dijkstra(0, n)
	for i, cost := range dist {
		fmt.Printf("%d %d\n", i, cost)
	}
}

Python: import sys

def dijkstra(v_count: int, edges: list, start: int,
             *, adj_matrix: bool = False, unreachable=float("inf")) -> list:
    """ ダイクストラ法
    :param v_count: 頂点数
    :param edges: 辺のリスト(隣接リストor隣接行列)
    :param start: スタートする頂点
    :param adj_matrix: edgesに渡したリストが隣接行列ならTrue
    :param unreachable: 到達不能を表すコスト値
                        隣接行列の辺の有無の判定および返すリストの初期値に使用
    """
    from heapq import heappush, heappop

    vertices = [unreachable] * v_count
    vertices[start] = 0
    q, rem = [(0, start)], v_count - 1

    while q and rem:
        cost, v = heappop(q)
        if vertices[v] < cost:
            continue
        rem -= 1

        dests = (filter(lambda x: x[1] != unreachable, enumerate(edges[v]))
                 if adj_matrix else edges[v])

        for dest, _cost in dests:
            newcost = cost + _cost
            if vertices[dest] > newcost:
                vertices[dest] = newcost
                heappush(q, (newcost, dest))

    return vertices

n = int(input())
inf = float("inf")
edges = [[inf]*n for _ in [0]*n]
for a in (tuple(map(int, l.split())) for l in sys.stdin):
    _from = a[0]
    for to, cost in zip(a[2::2], a[3::2]):
        edges[_from][to] = cost
vertices = dijkstra(n, edges, 0, adj_matrix=True)
for i, n in enumerate(vertices):
    print(i, n)

Python: #!/usr/bin/env python
# -*- coding: utf-8 -*-

import sys

WHITE, GRAY, BLACK = 0, 1, 2
D_MAX = int(1e7 + 1)


def generate_adj_matrix(v_info):
    for v_detail in v_info:
        v_index = int(v_detail[0])
        v_adj_length = int(v_detail[1])
        v_adj_list = v_detail[2:]
        # assert len(v_adj_list) == v_adj_length * 2
        for j in range(0, v_adj_length * 2, 2):
            init_adj_matrix[v_index][v_adj_list[j]] = int(v_adj_list[j + 1])

    return init_adj_matrix


def dijkstra_path():
    path_list[0] = 0

    while True:
        min_cost = D_MAX
        current_vertex = None
        for i in range(vertices_num):
            if color[i] is not BLACK and path_list[i] < min_cost:
                min_cost = path_list[i]
                current_vertex = i

        if min_cost == D_MAX:
            break

        color[current_vertex] = BLACK

        for adj_vertex in range(vertices_num):
            current_v_weight = adj_matrix[current_vertex].get(str(adj_vertex), -1)
            if current_v_weight < 0:
                continue
            elif color[adj_vertex] is not BLACK:
                if path_list[current_vertex] + current_v_weight < path_list[adj_vertex]:
                    path_list[adj_vertex] = path_list[current_vertex] + current_v_weight
                    parent_list[adj_vertex] = current_vertex
                    color[adj_vertex] = GRAY

    return path_list


if __name__ == '__main__':
    _input = sys.stdin.readlines()
    vertices_num = int(_input[0])
    init_vertices_table = list(map(lambda x: x.split(), _input[1:]))
    # assert len(init_vertices_table) == vertices_num

    parent_list, path_list = [-1] * vertices_num, [D_MAX] * vertices_num
    color = [WHITE] * vertices_num
    init_adj_matrix = tuple({} for _ in range(vertices_num))
    adj_matrix = generate_adj_matrix(init_vertices_table)
    ans = dijkstra_path()
    for j in range(vertices_num):
        print(j, ans[j])

Python: from collections import deque
INF = float("inf")
def MAIN():
    n = int(input())
    G = [[i, INF] for i in range(n)]
    G[0][1] = 0
    m = {}
    for _ in range(n):
        A = list(map(int, input().split()))
        m[A[0]] = {}
        for i in range(2, len(A), 2):
            m[A[0]][A[i]] = A[i + 1]
    dp = deque([0])
    while dp:
        u = dp.popleft()
        for v, c in m[u].items():
            if G[v][1] > G[u][1] + c:
                G[v][1] = G[u][1] + c
                dp.append(v)
    print("\n".join(" ".join(map(str, a)) for a in G))
MAIN()

Python: from sys import stdin
from collections import defaultdict
from heapq import heappush, heappop
import math

n = int(input())
g = defaultdict(list)

for i in range(n):
    l = list(map(int, stdin.readline().split()))
    s = l[0]
    k = l[1]
    t = l[2:]
    for j in range(0, 2*k, 2):
        g[s].append((t[j+1], t[j]))

d = [float('inf')] * 100
d[0] = 0
heap = [(d[0], 0)]

while heap:

    du, u = heappop(heap)
    for length, v in g[u]:

        if d[v] > du + length:
            d[v] = du + length
            heappush(heap, (d[v], v))

for i in range(n):
    print('{0} INF' if math.isinf(d[i]) else '{0} {1}'.format(i, d[i]))

Python: # -*- coding: utf-8 -*-
"""
Created on Sat Jul 14 19:11:44 2018

@author: maezawa
"""
infinity = 2*10**9

n = int(input())
adj = [[] for _ in range(n)]

for j in range(n):
    ain = list(map(int, input().split()))
    u = ain[0]
    k = ain[1]
    for i in range(2,2+2*k,2):
        adj[u].append([ain[i],ain[i+1]])
    #print(*adj[u])

color = [0]*n
d = [infinity for _ in range(n)]
p = [0]*n
p[0] = -1
d[0] = 0

def dyk(s):
    cnt = 1
    cur = s
    candidates = [] # remaining nodes
    while True:
        for i, w in adj[cur]:
            if color[i] == 2:
                continue
            if d[i] > d[cur] + w:
                d[i] = d[cur] + w
                color[i] = 1
            candidates.append(i)
        min_d = infinity
        for j in candidates:
            if min_d > d[j]:
                min_node = j
                min_d = d[j]
        candidates.remove(min_node)
        p[min_node] = cur
        color[cur] = 2
        cur = min_node
        cnt += 1
        #print(cur, d)
        if cnt == n:
            break
    return

dyk(0)
for i in range(n):
    print(i, d[i])

Python: from collections import defaultdict

n = int(input())
graph = defaultdict(list)
for _ in range(n):
    u, k, *edges = map(int, input().split())
    for i in range(0, len(edges), 2):
        graph[u].append((edges[i], edges[i+1]))

# print(graph)

s = 0
d = [float('inf')] * (n)
fixed = [False] * (n)
d[0] = 0

while True:
    u = None
    d_min = float('inf')
    for i in range(len(d)):
        if not fixed[i] and d[i] < d_min:
            d_min = d[i]
            u = i

    if u is None:
        break            
    fixed[u] = True
    # print('fixed:', u)

    for v, w in graph[u]:
        if not fixed[v]:
            d[v] = min(d[v], d[u]+w)
    # print(d)

# print(d)

for i in range(len(d)):
    print(i, d[i])