Java 使用DFS检查无向图是否连通

Java 使用DFS检查无向图是否连通

介绍

这个Java程序使用DFS检查无向图是否连通。它从用户那里以图中顶点和边的数量的形式输入图的信息,以及边本身。它创建一个邻接表来存储图的边,然后使用DFS遍历图并检查是否所有顶点都被访问。

如果所有顶点都被访问,则图是连通的。该程序的时间复杂度为O(V+E),其中V是图中顶点的数量,E是图中边的数量,空间复杂度为O(V+E)。

定义

无向连通图是指所有顶点通过边连接在一起的图。在这样的图中,任意两个顶点之间都存在一条路径。如果我们从任意一个顶点出发,通过边遍历,可以到达图中的所有其他顶点。这个概念在图论中很重要,并且有许多应用,包括网络分析和地理地图。确定无向图的连通性是图论中的一个基本问题,存在多种算法可以解决。其中一种流行的算法是DFS,它可以用来确定无向图是否连通。

方法

  • 定义一个函数dfsTraversal,在给定的图中从给定的顶点开始执行DFS遍历。该函数接受三个参数-
  • 图 – 图的邻接表
  • 顶点 – 应从哪个顶点开始进行DFS遍历
  • visited – 一个包含布尔值的数组,指示某个顶点是否被访问过

dfsTraversal函数标记给定的顶点为已访问,并递归地访问其所有未访问的邻居。

  • 定义一个函数isConnected,检查给定的图是否连通。该函数接受两个参数-
  • 图 – 图的邻接表
  • 顶点 – 图中的顶点数量

isConnected函数初始化一个名为visited的布尔值数组,用于跟踪访问过的顶点。然后,它使用dfsTraversal函数从图的第一个顶点开始执行DFS遍历。最后,它检查是否所有顶点都被访问过。如果所有顶点都被访问,则图是连通的,函数返回true。否则,返回false。

  • 在主函数中-
  • 读取图中的顶点和边的数量。
  • 初始化邻接表图。
  • 读取图的边并将其添加到邻接表中。
  • 调用isConnected函数检查图是否连通,并根据结果打印结果。

这种方法背后的关键思想是使用深度优先搜索(DFS)访问图中的所有顶点并将它们标记为已访问。如果所有顶点都被访问过,那么图是连通的。如果没有,那么必定有一些顶点与图的其余部分不连接,这意味着图是不连通的。

示例1

下面是一个使用深度优先搜索(DFS)检查无向图是否连通的Java程序:

import java.util.*;

public class ConnectedGraphDFS {

   // function to perform DFS traversal on the graph
   private static void dfsTraversal(ArrayList<Integer>[] graph, int vertex, boolean[] visited) {
      visited[vertex] = true;

      // visit all the neighbors of the vertex
      for(int neighbor : graph[vertex]) {
         if(!visited[neighbor]) {
            dfsTraversal(graph, neighbor, visited);
         }
      }
   }

   // function to check whether the given graph is connected or not
   public static boolean isConnected(ArrayList<Integer>[] graph, int vertices) {
      boolean[] visited = new boolean[vertices];

      // perform DFS traversal from the first vertex
      dfsTraversal(graph, 0, visited);

      // check if all the vertices are visited or not
      for(int i = 0; i < vertices; i++) {
         if(!visited[i]) {
            return false;
         }
      }

      return true;
   }

   // main function to test the program
   public static void main(String[] args) {
      Scanner sc = new Scanner(System.in);

      // read the number of vertices in the graph
      System.out.print("Enter the number of vertices in the graph: ");
      int vertices = sc.nextInt();

      // read the number of edges in the graph
      System.out.print("Enter the number of edges in the graph: ");
      int edges = sc.nextInt();

      // initialize the adjacency list
      ArrayList<Integer>[] graph = new ArrayList[vertices];

      for(int i = 0; i < vertices; i++) {
         graph[i] = new ArrayList<Integer>();
      }

      System.out.println("Enter the edges of the graph:");
      // read the edges of the graph
      for(int i = 0; i < edges; i++) {
         int u = sc.nextInt();
         int v = sc.nextInt();

         // add edge between u and v
         graph[u].add(v);
         graph[v].add(u);
      }

      // check whether the graph is connected or not
      boolean isConnected = isConnected(graph, vertices);

      if(isConnected) {
         System.out.println("The graph is connected.");
      }
      else {
         System.out.println("The graph is not connected.");
      }
   }
}

说明

在这个程序中,我们首先定义了一个名为dfsTraversal的函数,它从给定的顶点开始对给定的图进行深度优先搜索遍历。这个函数有三个参数。dfsTraversal函数将给定的顶点标记为已访问,并递归地访问所有未访问的邻居。接下来,我们定义了一个名为isConnected的函数,它检查给定的图是否连通。这个函数有两个参数。

isConnected函数初始化了一个名为visited的布尔值数组,用于跟踪已访问的顶点。然后,它使用dfsTraversal函数从图的第一个顶点开始进行深度优先搜索遍历。最后,它检查所有的顶点是否都被访问过。如果所有的顶点都被访问过,则图是连通的,函数返回true。否则,返回false。

输出

Enter the number of vertices in the graph: 6
Enter the number of edges in the graph: 5
Enter the edges of the graph:
0 1
1 2
2 3
4 5
5 4

Graph is not connected

示例2

这是另一个使用深度优先搜索(DFS)来检查无向图是否连通的Java程序 –

import java.util.ArrayList;
import java.util.Scanner;

public class GraphConnectivityDFS {
   private int V;
   private ArrayList<ArrayList<Integer>> adj;

   GraphConnectivityDFS(int v) {
      V = v;
      adj = new ArrayList<>(V);
      for (int i = 0; i < V; ++i) {
         adj.add(new ArrayList<>());
      }
   }

   void addEdge(int v, int w) {
      adj.get(v).add(w);
      adj.get(w).add(v);
   }

   void dfsTraversal(int v, boolean[] visited) {
      visited[v] = true;
      for (int n : adj.get(v)) {
         if (!visited[n]) {
            dfsTraversal(n, visited);
         }
      }
   }

   boolean isConnected() {
      boolean[] visited = new boolean[V];
      dfsTraversal(0, visited);
      for (int i = 0; i < V; ++i) {
         if (!visited[i]) {
            return false;
         }
      }
      return true;
   }

   public static void main(String[] args) {
      Scanner scanner = new Scanner(System.in);

      System.out.print("Enter the number of vertices in the graph: ");
      int V = scanner.nextInt();

      System.out.print("Enter the number of edges in the graph: ");
      int E = scanner.nextInt();

      GraphConnectivityDFS graph = new GraphConnectivityDFS(V);

      System.out.println("Enter the edges of the graph:");
      for (int i = 0; i < E; i++) {
         int v = scanner.nextInt();
         int w = scanner.nextInt();
         graph.addEdge(v, w);
      }

      boolean connected = graph.isConnected();
      if (connected) {
         System.out.println("Graph is connected");
      } else {
         System.out.println("Graph is not connected");
      }
   }
}

输出

Enter the number of vertices in the graph: 2
Enter the number of edges in the graph: 2
Enter the edges of the graph:
0 1
1 0
Graph is connected

结论

  • 无向连通图是一种图,其中所有顶点互相连接,并且任意两个顶点之间存在路径。

  • 确定无向图的连通性是图论中的一个重要问题,存在各种算法来解决它,例如上述Java程序中使用的DFS算法。

Camera课程

Python教程

Java教程

Web教程

数据库教程

图形图像教程

办公软件教程

Linux教程

计算机教程

大数据教程

开发工具教程