Go: package main

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

var scanner = bufio.NewScanner(os.Stdin)

func nextString() string {
	scanner.Scan()
	return scanner.Text()
}

func nextInt() int {
	n, err := strconv.Atoi(nextString())
	if err != nil {
		fmt.Printf("strconv.Atoi failed: %v\n", err)
	}
	return n
}

func newGraph(nNodes int) *Graph {
	g := Graph{}
	g.nodes = make([]*GraphNode, nNodes)
	for iNode := 0; iNode < len(g.nodes); iNode++ {
		g.nodes[iNode] = &GraphNode{}
		g.nodes[iNode].key = GraphNodeKey(iNode)
	}
	return &g
}

var infty = 1000000000

type GraphNodeKey int

// GraphNode is a node for undirected graph
type GraphNode struct {
	key       GraphNodeKey
	adjacents []*GraphNode
	visited   bool
	d, f      int
	parent    *GraphNode
	cc        int
}

func (g *Graph) setAdjacent(l, r GraphNodeKey) {
	g.nodes[l].adjacents = append(g.nodes[l].adjacents, g.nodes[r])
}

// Graph is a undirected graph
type Graph struct {
	nodes []*GraphNode
}

func (g *Graph) initialize() {
	for iNode := 0; iNode < len(g.nodes); iNode++ {
		g.nodes[iNode].visited = false
		g.nodes[iNode].d = infty
		g.nodes[iNode].f = infty
		g.nodes[iNode].parent = nil
		g.nodes[iNode].cc = -1 // 22.3-12
	}
}

type QueueEntry struct {
	node *GraphNode
	next *QueueEntry
}

type Queue struct {
	head, tail *QueueEntry
}

func (q *Queue) enqueue(node *GraphNode) {
	entry := QueueEntry{}
	entry.node = node

	if q.tail == nil {
		q.head = &entry
		q.tail = &entry
		return
	}

	q.tail.next = &entry
	q.tail = q.tail.next
}

func (q *Queue) dequeue() *QueueEntry {
	if q.head == nil {
		return nil
	}
	poped := q.head
	q.head = q.head.next
	if q.head == nil {
		q.tail = nil
	}
	return poped
}

func (q *Queue) isEmpty() bool {
	return q.head == nil
}

var time = 0

func fillDistancesByDepthFirstSearch(g *Graph) {
	g.initialize()
	time = 0
	cc := 0

	for _, u := range g.nodes {
		if !u.visited {
			dfsVisit(g, u, cc)
			cc++
		}
	}
}

func dfsVisit(g *Graph, u *GraphNode, cc int) {
	time++
	u.d = time
	u.cc = cc

	u.visited = true
	for _, v := range u.adjacents {
		if !v.visited {
			v.parent = u
			dfsVisit(g, v, cc)
		}
	}
	time++
	u.f = time
}

func main() {
	scanner.Split(bufio.ScanWords)

	nUsers := nextInt()
	nEdges := nextInt()
	graph := newGraph(nUsers)
	for iEdge := 0; iEdge < nEdges; iEdge++ {
		l := GraphNodeKey(nextInt())
		r := GraphNodeKey(nextInt())
		graph.setAdjacent(l, r)
		graph.setAdjacent(r, l)
	}

	fillDistancesByDepthFirstSearch(graph)

	nQueries := nextInt()
	for iQuery := 0; iQuery < nQueries; iQuery++ {
		l := GraphNodeKey(nextInt())
		r := GraphNodeKey(nextInt())

		// fmt.Println(graph.nodes[l].d, graph.nodes[r].d, graph.nodes[r].f, graph.nodes[l].f)
		if graph.nodes[l].cc == graph.nodes[r].cc {
			fmt.Println("yes")
		} else {
			fmt.Println("no")
		}
	}
}

C++: #include<iostream>
#include<vector>
#include<stack>
#include<set>
using namespace std;

bool DFS(vector<vector<int> >& G, int a, int b) {
    if (G[a].size() == 0) return false;

    stack<pair<int, int> > S;
    vector<bool> is_visited(G.size(), false);
    int idx = 0;
    do {
        if (idx >= G[a].size()) {
            a   = S.top().first;
            idx = S.top().second;
            S.pop();
            idx++;
            continue;
        }
        if (G[a][idx] == b) return true;
        if (!is_visited[G[a][idx]]) {
            is_visited[G[a][idx]] = true;
            S.push(make_pair(a, idx));
            a   = G[a][idx];
            idx = 0;
            continue;
        }
        idx++;
    } while (!S.empty());
    return false;
}


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

    vector<vector<int> > G(n);
vector<vector<bool> > D(100000, vector<bool>(100000));

    for (int i = 0; i < m; i++) {
        int a, b;
        cin >> a >> b;
        G[a].push_back(b);
        G[b].push_back(a);
    }

// for (int i = 0; i < n; i++) {
//     cout << i << " : ";
//     for (set<int>::iterator it = G[i].begin(); it != G[i].end(); it++){
//         cout << *it << " ";
//     }
//     cout << endl;
// }

    int q;
    cin >> q;
    for (int i = 0; i < q; i++) {
        int a, b;
        cin >> a >> b;
        if (DFS(G, a, b)) {
           cout << "yes" << endl;
        } else {
           cout << "no"  << endl;
        }
    }
    return 0;
}

C++: #include <stdio.h>
#include <stdlib.h>

int n, m;

void merge(int *u, int *net, int oldnet, int newnet);

int main(int argc, char *argv[])
{
  int i, s, t, p, q;
  int *u;
  int *net;

  scanf("%d", &n);
  scanf("%d", &m);
  u = (int *)malloc(sizeof(int) * n);
  net = (int *)malloc(sizeof(int) * (m + 1));
  for (i = 0; i < n; i++) u[i] = -1;
  for (i = 0; i <= m; i++) net[i] = 0;

  p = 1;

  for (i = 0; i < m; i++) {
    scanf("%d", &s);
    scanf("%d", &t);
    if (s != t) {
      if (u[s] == -1 && u[t] == -1) {
    u[s] = p;
    u[t] = p;
    net[p] += 2;
    p++;
      } else {
    if (u[s] != -1 && u[t] == -1) {
      u[t] = u[s];
      net[u[s]]++;
    } else if (u[s] == -1 && u[t] != -1) {
      u[s] = u[t];
      net[u[t]]++;
    } else {
      if (u[s] != u[t]) {
        if (net[u[s]] > net[u[t]]) merge(u, net, u[t], u[s]);
        else merge(u, net, u[s], u[t]);
      }
    }
      }
    }
  }

  scanf("%d", &q);

  for (i = 0; i < q; i++) {
    scanf("%d", &s);
    scanf("%d", &t);

    if (s == t) printf("yes\n");
    else {
      if (u[s] == u[t] && u[s] != -1 && u[t] != -1) printf("yes\n");
      else printf("no\n");
    }
  }

  return 0;
}

void merge(int *u, int *net, int oldnet, int newnet)
{
  int i;

  for (i = 0; i < n; i++) {
    if (u[i] == oldnet) u[i] = newnet;
  }

  net[newnet] += net[oldnet];
  net[oldnet] = 0;
}

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

using namespace std;

#define GRAPH_SIZE 100000

enum state_t {
  WHITE,
  GRAY,
  BLACK,
};

struct vertex_t {
  uint32_t color;
  vector<uint32_t> connections;
};

static vertex_t graph[GRAPH_SIZE];
static state_t state[GRAPH_SIZE];

static void colorize(uint32_t index, uint32_t color)
{
  if (state[index] == WHITE) {
    state[index] = GRAY;
    graph[index].color = color;
    for (uint32_t i = 0; i < graph[index].connections.size(); i++) {
      colorize(graph[index].connections[i], color);
    }
    state[index] = BLACK;
  }
}

void check_connection(size_t num)
{
  for (uint32_t i = 0; i < num; i++) {
    state[i] = WHITE;
  }

  uint32_t color = 1;
  for (uint32_t i = 0; i < num; i++) {
    colorize(i, color);
    color++;
  }
}

#include <iostream>

int32_t main()
{
  uint32_t n, m;
  cin >> n >> m;

  for (uint32_t i = 0; i < m; i++) {
    uint32_t index, to;
    cin >> index >> to;
    graph[index].connections.push_back(to);
  }

  check_connection(n);

  uint32_t qs;
  cin >> qs;

  for (uint32_t i = 0; i < qs; i++) {
    uint32_t from, to;
    cin >> from >> to;

    if (graph[from].color == graph[to].color) {
      cout << "yes" << endl;
    } else {
      cout << "no" << endl;
    }
  }

  return 0;
}