Go: package main

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

func getScanner(fp *os.File) *bufio.Scanner {
	scanner := bufio.NewScanner(fp)
	scanner.Split(bufio.ScanWords)
	scanner.Buffer(make([]byte, 500001), 500000)
	return scanner
}

func getNextString(scanner *bufio.Scanner) string {
	scanner.Scan()
	return scanner.Text()
}

func getNextInt(scanner *bufio.Scanner) int {
	i, _ := strconv.Atoi(getNextString(scanner))
	return i
}

func main() {
	fp := os.Stdin
	if len(os.Args) > 1 {
		fp, _ = os.Open(os.Args[1])
	}

	scanner := getScanner(fp)
	writer := bufio.NewWriter(os.Stdout)

	n := getNextInt(scanner)
	nodes := make([]Node, n)

	for i := 0; i < n; i++ {
		nodes[i].list = make([]int, 0)
		nodes[i].d = -1
	}

	for i := 0; i < n; i++ {
		u := getNextInt(scanner)
		k := getNextInt(scanner)
		u--
		for ii := 0; ii < k; ii++ {
			v := getNextInt(scanner)
			v--
			nodes[u].list = append(nodes[u].list, v)
		}
	}

	queue := make([]int, n)
	queue[0] = 0
	nodes[0].d = 0
	d := 0
	i, j := 0, 1
	for i < j {
		d++
		prev := j
		for i < prev {
			for k, l := 0, len(nodes[queue[i]].list); k < l && i < n; k++ {
				if nodes[nodes[queue[i]].list[k]].d != -1 {
					continue
				}
				nodes[nodes[queue[i]].list[k]].d = d
				queue[j] = nodes[queue[i]].list[k]
				j++
			}
			i++
		}
	}

	for i := 0; i < n; i++ {
		fmt.Fprintln(writer, fmt.Sprintf("%d %d", i+1, nodes[i].d))
	}

	writer.Flush()
}

// Node ...
type Node struct {
	list []int
	d    int
}

C++: #include<cstdio>
#include<vector>
#include<algorithm>
#include<utility>
#include<numeric>
#include<iostream>
#include<array>
#include<string>
#include<sstream>
#include<stack>
#include<queue>
#include<list>
#define _USE_MATH_DEFINES

#include<math.h>
#include<map>

#define SENTINEL 1000000001

#define min(a,b) (a)>(b)?(b):(a)
#define max(a,b) (a)>(b)?(a):(b)

using namespace std;

int G[101][101];
int d[101];
bool checked[101];

int main()
{
	int n;
	cin >> n;

	for (int i = 0; i < n; i++)
	{
		int id, k;
		cin >> id >> k;

		for (int i = 0; i < k; i++)
		{
			int v;
			cin >> v;
			G[id][v] = 1;
		}
	}

	for (int i = 1; i <= 100; i++)
	{
		d[i] = -1;
	}

	queue<int> q;
	q.push(1);

	int td = 0;
	while (q.size() != 0)
	{
		int size = q.size();
		for (int i = 0; i < size; i++)
		{
			int id = q.front();
			q.pop();
			if (checked[id])
			{
				continue;
			}
			d[id] = td;
			checked[id] = true;
			for (int j = 1; j <= n; j++)
			{
				if (G[id][j] == 1 && !checked[j])
				{
					q.push(j);
				}
			}
		}
		td++;
	}

	for (int i = 1; i <= n; i++)
	{
		printf("%d %d\n", i, d[i]);
	}

	return 0;
}

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

using namespace std;

int d[100];
vector<int> adj[100];

void bfs(int n, int start) {
	queue<int> que;

	for (int i = 0; i < n; i++)
		d[i] = i == start ? 0 : -1;

	que.push(start);
	while(!que.empty()) {
		int from = que.front();
		que.pop();

		for (int& to : adj[from])
			if (d[to] == -1) {
				d[to] = d[from] + 1;
				que.push(to);
			}
	}
}

int main() {
	int n;

	cin >> n;

	for (int i = 0; i < n; i++) {
		int u, k;
		cin >> u >> k;
		while (k--) {
			int v;
			cin >> v;
			adj[u - 1].push_back(v - 1);
		}
	}

	bfs(n, 0);

	for (int i = 0; i < n; i++)
		cout << i + 1 << " " << d[i] << endl;

	return 0;
}

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

using namespace std;

static const int N = 100;
static const int INFTY = (1<<21);

int n, M[N][N];
int d[N];

void bfs(int s) 
  queue<int> q;

  q.push(s);
  for (int i = 0; i < n; i++) {
    d[i] = INFTY; 
  }
  d[s] = 0;
  int u;
  while (!p.empty()) {
    u = q.front(); q.pop();
    for (int v = 0; v < n; v++) {
      if (M[u][v] == 0) {
        continue;
      }
      if (d[v] != INFTY) {
        continue;
      }
      d[v] = d[u] + 1;
      q.push(v);
    }
  }
  for (int i = 0; i < n; i++) {
    cout << i + 1 << " " << ((d[i] == INFTY) ? (-1) : d[i]) << endl;
  }
}

int main() {

  cin >> n;
  for (int i = 0; i < n; i++) {
    for (int j = 0; j < n; j++) {
      M[i][j] = 0;
    }
  }

  int u, k, v;
  for (int i = 0; i < n; i++) {
    cin >> u >> k;
    u--; // to 0 origin
    for (int j = 0; j < n; j++) {
      cin >> v;
      v--; // to 0 origin
      M[u][v] = 1;
    }
  }

  bfs(0);

  return 0;
}

C++: #include <stdio.h>

#define N 100     
#define SUCCESS 1 // 成功
#define FAILURE 0 // 失敗
#define INFTY 1 << 21 // 到達不可能を表す大きな値

int queue[N]; // キューの本体
int queue_head = 0; // データ先頭
int queue_num; // データ個数

int node_num, M[N][N];
int d[N]; // 距離で訪問状態(color)を管理する

int enqueue(int enq_data) // キューにデータを追加する
{
  if (queue_head + queue_num < N) {
    queue[queue_head + queue_num] = enq_data;
    queue_num++;
    return SUCCESS;
  } else {
    return FAILURE;
  }
}

int dequeue(int *deq_data) // キューからデータを取り出す
{
  if (queue_num > 0) {
    *deq_data = queue[queue_head];
    queue_num--;
    queue_head++;
    return SUCCESS;
  } else {
    return FAILURE;
  }
}

void bfs(int s) {
  enqueue(s); // 始点をキューに入れる
  for (int i = 1; i <= node_num; i++) d[i] = INFTY; // とりあえず全部INFTYにする
  d[s] = 0; // 始点から自分自身までの距離は0
  int u, p;
  while(queue_num > 0) { // キューが空でない間繰り返す
    u = queue[queue_head]; // キューの先頭からノードを取り出し，訪問
    dequeue(&p); // 同上
    for (int v = 1; v <= node_num; v++) {
        if (M[u][v] == 0) continue; // キュー先頭のノードとvが繋がってないならこのループは終了
        if (d[v] != INFTY) continue; // 既に距離を決めているならこのループは終了
        d[v] = d[u] + 1; // 次に訪問するノードまでの距離は，それまでの距離+1
        enqueue(v); // uに繋がっているノードは将来訪問しないといけない
    }
  }
  for (int i = 1; i <= node_num; i++) { // 表示部
    printf("%d %d\n", i, d[i]);
  }
}

// mainの流れはdfsと同じ(隣接行列の初期化→隣接行列にノード間の接続関係を登録→bfsを呼び出す)
int main(void)
{
  int u, v, k, i, j;
  
  scanf("%d", &node_num);
  for (i = 0; i <= node_num; i++) {
    for(j = 0; j <= node_num; j++) M[i][j] = 0;
  }

  for (i = 0; i < node_num; i++) {
    scanf("%d %d", &u, &k);
    for (j = 0; j < k; j++) {
      scanf("%d", &v);
      M[u][v] = 1;
    }
  }

  bfs(1);
  
  return 0;
}

C++: #include<bits/stdc++.h>
using namespace std;
int main(){
  int n,lis[111][111]={},d[111];
  for(int i=0;i<111;i++)d[i]=-1;
  cin>>n;
  for(int c=0;c<n;c++){
    int u,k,v;
    cin>>u>>k;
    for(int i=0;i<k;i++){
      cin>>v;
      lis[u][v]=1;
    }
  }
  queue< pair<int,int> > q;
  q.push(make_pair(1,0));
  while(!q.empty()){
    int from=q.front().first;
    int m=q.front().second;
    q.pop();
    if(d[from]==-1){
      d[from]=m;
      for(int i=1;i<=n;i++){
	if(lis[from][i])q.push(make_pair(i,m+1));
      }
    }
  }
  for(int i=1;i<=n;i++)cout<<i<<" "<<d[i]<<endl;
  return 0;
}

C++: #include "stdafx.h"
#include <iostream>
#include <string>
#include <vector>
#include <algorithm>
#include <queue>
#include <stdio.h>
#define REP(i, n) for(int i = 0;i < n;i++)

using namespace std;

static const int N = 100;
static const int INFTY = (1 << 21);

int n, M[N][N];
int d[N];

void bfs(int s)
{
	queue<int>	q;
	q.push(s);
	REP(i, n)
		d[i] = INFTY;
	d[s] = 0;
	int u;

	while (!q.empty)
	{
		u = q.front();
		q.pop();
		REP(v, n)
		{
			if (M[u][v] == 0)
				continue;
			if (d[v] != INFTY)
				continue;
			d[v] = d[u]++;
			q.push(v);
		}
	}
	REP(i, n)
		cout << i++ << " " << ((d[i] == INFTY) ? (-1) : d[i]) << endl;
}

int main()
{
	int u, k, v;

	cin >> n;

	REP(i, n)
	{
		REP(j, n)
			M[n][n] = 0;
	}

	REP(i, n)
	{
		cin >> u >> k;
		u--;
		REP(i, k)
		{
			cin >> v;
			v--;
			M[u][v] = 1;
		}
	}

	bfs(0);
	return 0;
}