图的深度(递归/非递归)深度优先遍历和队列辅助的广度优先遍历

 1、深度遍历

   1.1 递归:

              对于当前节点i; 若节点j与节点i有连接,且j没有被遍历过,则遍历j;

              伪代码:

dfsRecur(i){ 
  for j <- 1:n
     if(j isChild(i) && j not walked)
        dfsRecur(j);
}

      

  1.2 非递归(基于栈):

              从源节点出发,对于每一个节点i,如果i有子节点j(且j没有别便历过),就将i入栈;否则(到达末节点),i出栈;从栈内取出顶节点作为节点i,循环遍历至栈内没有节点。

              伪代码:

dfsOnStack(){ 
  i <- 1
  stack.add(i);
  while(stack is not empty){
     j <- 1:n
     do
          stack.add(j)   if(j isChild(i) && j not ergodiced)
           i <- j;       otherwise
  }
}

       

2、广度遍历(基于队列)

   2.1 基本思想

           逐层遍历图:

            i) 从源节点出发,源节点为第一层;

           ii) 对于第i层的队列

                遍历第i层的所有元素,其下一届点全部放入第i+1层队列

  3、代码实现(JAVA)


import java.util.ArrayList;
import java.util.Arrays;
import java.util.Comparator;
import java.util.List;
import java.util.PriorityQueue;
import java.util.Scanner;
import java.util.Stack;
/*
 * DFS
 */
public class Main {
	
	public static void main(String[] args) {
		int[][] a = { 	{ 0, 1, 1, 0, 1 },
				   		{ 1, 0, 1, 1, 0 },
				   		{ 1, 1, 0, 0, 0 },
				   		{ 0, 1, 0, 0, 0 },
				   		{ 1, 0, 0, 0, 0 }};
//		dfs(a);
//		int l = depthOf(a);
//		
//		dfsDepth(a);
//		dfs1(a);
//		System.out.println(l);
		bfsDepth(a);
	}
	/*
	 * 求深度
	 */
	private static int depthOf(int[][] a) {
		boolean[] have = new boolean[a[0].length];
		return depthOf(a, 0, have);
	}
	private static int depthOf(int[][] a, int i, boolean[] have) {
		have[i] = true;
		int d = 0;
		int t = 0;
		for (int j = 0; j < have.length; j++) {
			if(j!=i && a[i][j]==1 && !have[j]) {
				t = depthOf(a, j, have);
				if(t > d)
					d = t;
			}
		}
		return d+1;
	}
	
	/*
	 * 递归dfs
	 */
	private static void dfs(int[][] a) {
		boolean[] have = new boolean[a[0].length];
		dfs(a, 0, have);
		System.out.println();
	}
	private static void dfs(int[][] a, int i, boolean[] have) {
		System.out.print(i+"->");
		have[i] = true;
		for (int j = 0; j < have.length; j++) {
			if(j!=i && a[i][j]==1 && !have[j])
				dfs(a, j, have);
		}
		
	}
	
	
	/*
	 * 递归dfs+depth
	 */
	private static void dfsDepth(int[][] a) {
		int[] depth = new int[a[0].length];
		depth[0] = 1;
		dfs(a, 0, depth);
		System.out.println();
		for (int i : depth) {
			System.out.println(i);
		}
	}
	private static void dfs(int[][] a, int i, int[] depth) {
		System.out.print(i+"->");
		for (int j = 0; j < depth.length; j++) {
			if(j!=i && a[i][j]==1 && depth[j] == 0) {
				depth[j] = depth[i]+1;
				dfs(a, j, depth);
			}
				
		}
		
	}
	
	/*
	 * 非递归dfs遍历
	 */
	private static void dfs1(int[][] a) {
		int[] depth = new int[a[0].length];
		depth[0] = 1;
		int i = 0;//当前节点中间变量 
		int t = 0; //下一节点中间变量 
		Stack<Integer> s = new Stack<Integer>();
		while(true) {
			t = hasNext(a, i, depth);
			if (t != -1) {
				s.add(i);
				i = t;
			}
			else {
				System.out.print(i+"->");
				if(s.empty())
					break;
				i = s.pop();
			}
			
		}
		System.out.println();
		
		for (int n : depth) {
			System.out.println(n);
		}
	}
	private static int hasNext(int[][] a, int i, int[] depth) {
		for (int j = 0; j < depth.length; j++) {
			if(j!=i && a[i][j]==1 && depth[j] == 0) {
				depth[j] = depth[i]+1;
				return j;
			}
		}
		return -1;
	}
	
	
	
	/*
	 * 递归bfs+depth
	 */
	private static void bfsDepth(int[][] a) {
		int[] depth = new int[a[0].length];
		depth[0] = 1;
		List<Integer> listCur = new ArrayList<Integer>();//当前层
		List<Integer> listNext = new ArrayList<Integer>();//当前层
		listCur.add(0);
		while(!listCur.isEmpty()){
			for (int i = 0; i < listCur.size(); i++) {
				System.out.print(listCur.get(i)+"->");
				for (int j = 0; j < a.length; j++) {
					if(a[listCur.get(i)][j] == 1 && depth[j] == 0) {
						listNext.add(j);
						depth[j] = depth[listCur.get(i)]+1;
					}
				}
			}
			listCur = listNext;
			listNext = new ArrayList<Integer>();
		}
	}

}

代码里所有的边的值为1;若果不为1,if语句里的判断条件a[i][j]==1对应修改就好。 

 

    原文作者:数据结构之图
    原文地址: https://blog.csdn.net/alixia111/article/details/82495046
    本文转自网络文章,转载此文章仅为分享知识,如有侵权,请联系博主进行删除。
点赞

发表评论

电子邮件地址不会被公开。 必填项已用*标注