Go: // Warshall–Floyd Algorithm

package main

import (
	"bufio"
	"fmt"
	"os"
	"strconv"
	"strings"
)

var scanner = bufio.NewScanner(os.Stdin)

const INF = 2000000000

func main() {
	for scanner.Scan() {
		buf := strings.Split(scanner.Text(), " ")
		n, _ := strconv.Atoi(buf[0])
		m, _ := strconv.Atoi(buf[1])
		if n == 0 && m == 0 {
			break
		}
		c_matrix := make([][]int, m)
		for i := range c_matrix {
			c_matrix[i] = make([]int, m)
		}
		t_matrix := make([][]int, m)
		for i := range t_matrix {
			t_matrix[i] = make([]int, m)
		}
		for i := 0; i < n; i++ {
			scanner.Scan()
			buf_ := strings.Split(scanner.Text(), " ")
			a, _ := strconv.Atoi(buf_[0])
			b, _ := strconv.Atoi(buf_[1])
			c, _ := strconv.Atoi(buf_[2])
			t, _ := strconv.Atoi(buf_[3])
			c_matrix[a-1][b-1] = c
			t_matrix[a-1][b-1] = t
		}
		c_dist := make([][]int, m)
		c_prev := make([][]int, m)
		t_dist := make([][]int, m)
		t_prev := make([][]int, m)
		for i := 0; i < m; i++ {
			c_dist[i] = make([]int, m)
			c_prev[i] = make([]int, m)
			t_dist[i] = make([]int, m)
			t_prev[i] = make([]int, m)
		}
		for i := 0; i < m; i++ {
			for j := 0; j < m; j++ {
				if c_matrix[i][j] == 0 {
					c_dist[i][j] = INF
					c_prev[i][j] = -1
				} else {
					c_dist[i][j] = c_matrix[i][j]
					c_prev[i][j] = i
				}
				if t_matrix[i][j] == 0 {
					t_dist[i][j] = INF
					t_prev[i][j] = -1
				} else {
					t_dist[i][j] = t_matrix[i][j]
					t_prev[i][j] = i
				}
			}
			c_dist[i][i] = 0
			t_dist[i][i] = 0
		}
		for k := 0; k < m; k++ {
			for i := 0; i < m; i++ {
				for j := 0; j < m; j++ {
					c_newlen := c_dist[i][k] + c_dist[k][j]
					if c_newlen < c_dist[i][j] {
						c_dist[i][j] = c_newlen
						c_prev[i][j] = c_prev[k][j]
					}
				}
			}
		}
		for k := 0; k < m; k++ {
			for i := 0; i < m; i++ {
				for j := 0; j < m; j++ {
					t_newlen := t_dist[i][k] + t_dist[k][j]
					if t_newlen < t_dist[i][j] {
						t_dist[i][j] = t_newlen
						t_prev[i][j] = t_prev[k][j]
					}

				}
			}
		}
		scanner.Scan()
		k, _ := strconv.Atoi(scanner.Text())
		for i := 0; i < k; i++ {
			scanner.Scan()
			buf_ := strings.Split(scanner.Text(), " ")
			p, _ := strconv.Atoi(buf_[0])
			q, _ := strconv.Atoi(buf_[1])
			r, _ := strconv.Atoi(buf_[2])
			switch r {
			case 0:
				fmt.Println(c_dist[p-1][q-1])
			case 1:
				fmt.Println(t_dist[p-1][q-1])
			}
		}
	}
}

C++: #include <iostream>
#include <vector>
#include <cstring>
 
using namespace std;
 
#define loop(i,a,b) for(int i=(a); i<(int)(b); i++)
#define rep(i,b) loop(i,0,b)
 
 
struct edge {
    int from,to,money,time;
};
int d[2][101][101];
 
int main(){
    int n,m;
    while(cin>>n>>m, n|m){
        for(auto& arr:d[0]) for(int& i:arr) i=1<<28;
        for(auto& arr:d[1]) for(int& i:arr) i=1<<28;
        rep(i,m+1) d[0][i][i]=0;
        rep(i,m+1) d[1][i][i]=0;
        rep(i,n){
            int f,t,mo,ti; cin>>f>>t>>mo>>ti;
            d[0][f][t]=d[0][t][f]=mo;
            d[1][f][t]=d[1][t][f]=ti;
        }
        rep(k,m+1)rep(i,m+1)rep(j,m+1){
            d[0][i][j]=min(d[0][i][j], d[0][i][k]+d[0][k][j]);
            d[1][i][j]=min(d[1][i][j], d[1][i][k]+d[1][k][j]);
        }
        int k; cin>>k;
        rep(i,k){
            int p,q,r; cin>>p>>q>>r;
            cout<<d[r][p][q]<<endl;
        }
    }
}

C++: #include<iostream>
#include<queue>
#include<vector>
#include<map>
using namespace std;
typedef pair<int,int> P;
typedef struct{
	int next;
	int cost[2];
}edge;

int n,m;
vector<edge> mapp[111];
int bfs(int now,int goal,int k);

int main(){
	while(1){
		cin >> n >> m;
		if(n == 0 && m == 0) break;
		for(int i=0;i<n+1;i++){
			mapp[i].clear();
		}
		for(int i=0;i<n;i++){
			int a,b,cost,tim;
			cin >> a >> b >> cost >> tim;
			edge x;
			x.next = b; x.cost[0] = cost; x.cost[1] = tim;
			mapp[a].push_back(x);
		}
		int k;
		cin >> k;
		int ans;
		for(int i=0;i<k;i++){
			int p,q,r;
			cin >> p >> q >> r;
			if(r == 0) ans = bfs(p,q,r);
			else if(r == 1) ans = bfs(p,q,r);
			cout << ans << endl;
		}
	}
}

int bfs(int now,int goal,int k){
	priority_queue<P, vector<P>,greater<P> > que;
	que.push(P(0,now));
	while(!que.empty()){
		P p = que.top(); que.pop();
		int no = p.second;
		int co = p.first;
		if(no == goal) return co;
		int len=mapp[no].size();
		for(int i=0;i<len;i++){
			edge x = mapp[no][i];
			que.push(P(co+x.cost[k],x.next));
		}
	}
	return 0;
}

C++: #include<iostream>
#include<algorithm>
#include<climits>
using namespace std;
const int INF = INT_MAX/3;
const int MAXN = 200;
const int TIME = 1,COST = 0;
int graph[2][MAXN][MAXN];
int n,m,a,b,c,t;
void solve();
void init(){
  for(int i = 0;i < m;i++)
    for(int j = 0;j < m;j++)
      graph[0][i][j] =graph[0][j][i] = graph[1][j][i] = graph[1][i][j] = INF;
}
int main(){
  cin >> n >> m;
  init();
  for(int i = 0;i < n;i++){
    cin >> a >> b >> c >> t;
    graph[TIME][a-1][b-1] = graph[TIME][b-1][a-1] = t;
    graph[COST][a-1][b-1] = graph[COST][b-1][a-1] = c;
  }
  /*
  for(int i = 0;i < m;i++){
    for(int j = 0;j < m;j++){
      cout << graph[0][j][i] << ' ';
    }
    cout << endl;
  }
  */
  solve();
  /*
  for(int i = 0;i < m;i++){
    for(int j = 0;j < m;j++){
      cout << graph[0][j][i] << ' ';
    }
    cout << endl;
  }
  */

  int X;
  cin >> X;
  for(int i = 0;i < X;i++){
    cin >> a >> b >> c;
    cout << graph[c][a-1][b-1] << endl;
  }
  return 0;
}

void solve(){
  for(int k = 0;k < m;k++){
    for(int i = 0;i < m;i++){
      for(int j = 0;j < m;j++){
	graph[0][i][j] = min(graph[0][i][j],graph[0][i][k] + graph[0][k][j]);
	graph[1][i][j] = min(graph[1][i][j],graph[1][i][k] + graph[1][k][j]);
      }
    }
  }
}

C++: #include <iostream>
#include <vector>

using namespace std;
static const int INF = 99999999;
int n, m;

void Dijkstra(int start, int goal, vector< vector<int> >& Vec)
{
	vector<int> cost(m);
	vector<bool> use(m);
	for(int i = 0; i < m; ++i)
	{
		cost[i] = INF;
		use[i] = false;
	}
	cost[start] = 0;
	int res = 0;
	while(true)
	{
		int v = -1;
		for(int i = 0; i < m; ++i)
		{
			if(!use[i] && (v == -1 || cost[i] < cost[v]))
			{
				v = i;
			}
		}
		if(v == -1)
		{
			break;
		}
		use[v] = true;
		for(int i = 0; i < m; ++i)
		{
			cost[i] = min(cost[i], cost[v] + Vec[v][i]);
		}
	}
	cout << cost[goal] << endl;
}

void solve()
{
	while(cin >> n >> m, n || m)
	{
		vector< vector<int> > Cost(m, vector<int>(m));
		vector< vector<int> > Time(m, vector<int>(m));
		for(int i = 0; i < m; ++i)
		{
			for(int j = 0; j < m; ++j)
			{
				Cost[i][j] = INF;
				Time[i][j] = INF;
			}
		}
		for(int i = 0; i < n; ++i)
		{
			int from, to, cost, time;
			cin >> from >> to >> cost >> time;
			--from; --to;
			Cost[from][to] = cost;
			Cost[to][from] = cost;
			Time[from][to] = time;
			Time[to][from] = time;
		}
		int k;
		cin >> k;
		for(int i = 0; i < k; ++i)
		{
			int start, goal, pattern;
			cin >> start >> goal >> pattern;
			--start; --goal;
			if(pattern == 0)
			{
				Dijkstra(start, goal, Cost);
			}
			else if(pattern == 1)
			{
				Dijkstra(start, goal, Time);
			}
		}
	}
}

int main()
{
	solve();
	return(0);
}