Recorrido de gráficos - DFS, BFS

1. Recorrido del gráfico

Comienza desde un vértice en el gráfico para visitar el resto de los vértices en el gráfico, y cada vértice se visita solo una vez

Hay dos tipos de recorrido de gráfico: DFS recorrido primero en profundidad y BFS recorrido primero en anchura .

2. Travesía primero en profundidad

El recorrido primero en profundidad es un recorrido primero en profundidad, que es simplemente ir hasta el final cada vez. Recorrido de pedido anticipado similar al árbol binario

Ideas:
1. Tome un vértice como punto de inicio para el recorrido primero en profundidad y marque el vértice como visitado
2. Seleccione cualquier ruta desde el vértice como punto de inicio para recorrer hasta el final y marque los vértices visitados
3. Paso 2 Después de atravesar hasta el final Regrese al vértice anterior y repita el paso
24. Fin del recorrido de todos los vértices

De acuerdo con la idea transversal, este es un proceso recursivo, de hecho, DFS es básicamente lo mismo que retroceder.

Atravesar:

inserte la descripción de la imagen aquí

Tome este gráfico como un ejemplo para el recorrido primero en profundidad

	static void dfs(int[][] graph,int idx,boolean[]visit) {
    
    
		int len = graph.length;
		//访问过
	 if(visit[idx]) return;
	 //访问该顶点
	 System.out.println("V"+idx);
	 //标志顶点
	 visit[idx] = true;
	 for(int i = 1;i < len;i++) {
    
    
	 //访问该顶点相连的所有边
		 if(graph[idx][i] == 1) {
    
    
	 //递归进行dfs遍历
		 dfs(graph, i, visit);
		 }
	 }
			
	}

Resultados transversales:
V1
V2
V3
V4
V5
V6
V7
V8
V9

El código para crear el gráfico:

public static void main(String[] args) {
    
    
		Scanner scanner = new Scanner(System.in);
		//顶点数 以1开始
		int n = scanner.nextInt();
		int[][] graph = new int[n+1][n+1];
		//边数
		int m = scanner.nextInt();
		
		for(int i = 1;i <= m;i++) {
    
    
			int v1 = scanner.nextInt();
			int v2 = scanner.nextInt();
			graph[v1][v2] = 1;
			graph[v2][v1] = 1;
		}
		
		//标记数组 false表示未访问过 
		boolean[] visit = new boolean[n+1];
		dfs(graph, 1, visit);
		
	}

3. Usa DFS para determinar si hay un ciclo en un gráfico dirigido

Idea: Al atravesar un vértice, si hay otros vértices conectados que han sido visitados además del vértice anterior, debe haber un ciclo

	//默认无环
   static boolean flag = false;
	public static void main(String[] args) {
    
    
		Scanner scanner = new Scanner(System.in);
		//顶点数 以1开始
		int n = scanner.nextInt();
		int[][] graph = new int[n+1][n+1];
		//边数
		int m = scanner.nextInt();
		
		for(int i = 1;i <= m;i++) {
    
    
			int v1 = scanner.nextInt();
			int v2 = scanner.nextInt();
			graph[v1][v2] = 1;
			
		}
	 //标记数组 true为访问过
		boolean[] visit = new boolean[n+1];
		dfs(graph, 1, visit,1);
		if(flag) 
			System.out.println("有环");
		
	}
	
	static void dfs(int[][] graph,int idx,boolean[]visit,int parent) {
    
    
		int len = graph.length;
	
	 System.out.println("V"+idx);
	 //标记顶点
	 visit[idx] = true;
	 for(int i = 1;i < len;i++) {
    
    
		 //访问该顶点相连的所有边
		 if(graph[idx][i] == 1) {
    
    
		 if( !visit[i] ) {
    
    
		 dfs(graph, i, visit,idx);
		 }
		 else if(idx != i) {
    
    
			 flag = true;
		 }
		 }
	 }
	
	 
	}

Nota: Es un gráfico dirigido para juzgar si hay un ciclo, y un gráfico no dirigido para juzgar si hay un ciclo no tiene sentido, porque dos vértices cualesquiera con un camino pueden ser un ciclo.

4. Recorrido primero en anchura

El recorrido primero en anchura es el recorrido primero en anchura . Orden de recorrido similar al árbol binario

Ideas:
1. Tome un vértice como punto de partida para el recorrido primero en anchura y marque el vértice como visitado
2. Visite todos los vértices que están conectados al vértice y no hayan sido visitados y marque los vértices visitados
3. Visita con paso 2 El vértice obtenido es el punto de partida y repita los pasos 1 y 2.
4. Atraviese todos los vértices y termine

El recorrido es asistido por la cola, y el orden de salida de la cola es el resultado del recorrido primero en anchura.
inserte la descripción de la imagen aquí

Recorra
inserte la descripción de la imagen aquí
este gráfico como ejemplo, cree un gráfico por matriz de adyacencia y realice un recorrido BFS

	static void bfs(int[][] graph) {
    
    		
		int len = graph.length;
		//标记数组 false表示未访问过 
		boolean[] visit = new boolean[len];
		//辅助队列
		Queue<Integer> queue = new LinkedList<>();
		
		queue.offer(1);
		visit[1] = true;
		
		while(!queue.isEmpty()) {
    
    
			int num = queue.poll();
			System.out.println("V"+num);
					
			//遍历该顶点所有相连顶点
			for(int i = 1;i < len;i++) {
    
    
				//相连并且没有被访问过
				if(graph[num][i] == 1 && !visit[i]) {
    
    
					queue.offer(i);
					visit[i] = true;				
				}
			}
		}	
	}

Resultado transversal:
V1
V2
V6
V3
V7
V9
V5
V4
V8

El código para crear el gráfico.

public static void main(String[] args) {
    
    
		Scanner scanner = new Scanner(System.in);
		//顶点数 以1开始
		int n = scanner.nextInt();
		int[][] graph = new int[n+1][n+1];
		//边数
		int m = scanner.nextInt();
		
		for(int i = 1;i <= m;i++) {
    
    
			int v1 = scanner.nextInt();
			int v2 = scanner.nextInt();
			graph[v1][v2] = 1;
			graph[v2][v1] = 1;
		}
		bfs(graph);
	}

Supongo que te gusta

Origin blog.csdn.net/qq_52595134/article/details/123108852
Recomendado
Clasificación