深度优先遍历 广度优先遍历JAVA
来源:互联网 发布:土库曼斯坦 知乎 编辑:程序博客网 时间:2024/05/20 08:23
package graph;import java.util.ArrayList;import java.util.LinkedList;import java.util.List;/** * @Author GJL * @Desription * @Date 2017/11/25 * @Modified By: **/public class BFS { public static void main(String[] args) { Graph graph = new Graph(6); graph.addNode(new GraphNode("A")); graph.addNode(new GraphNode("B")); graph.addNode(new GraphNode("C")); graph.addNode(new GraphNode("D")); graph.addNode(new GraphNode("E")); graph.addNode(new GraphNode("F")); graph.addEdge(0,1); graph.addEdge(0,2); graph.addEdge(0,3); graph.addEdge(1,4); graph.addEdge(2,4); graph.addEdge(3,4); graph.addEdge(4,5); //graph.bfs(0); graph.printMatrx(); System.out.println(); graph.dfs(0); }}class Graph{ //保存节点的数组 GraphNode [] graphNodes; //初始化时候 数组的大小 int size; //加入节点时候 已经存在的节点数 int curSize; //保存节点之间的联通关系 int[][] relation; public Graph(int size) { this.graphNodes = new GraphNode[size]; this.size = size; this.curSize = 0; this.relation = new int[size][size]; } public void addNode(GraphNode graphNode){ if(curSize<=size){ graphNodes[curSize++] = graphNode; }else{ System.out.println("节点数组已满"); } } public void addEdge(int start,int end){ if(start<size && end<size){ relation[start][end] = 1; relation[end][start] = 1; }else{ System.out.println("请输入正确的start end"); } } /** * @param nodeIndex 节点数组下标 */ public void bfs(int nodeIndex){ //利用队列 来存储那些与 已经遍历节点的相连节点索引 LinkedList list = new LinkedList(); //节点设置访问值为 true 节点索引入队列 graphNodes[nodeIndex].setVisted(true); list.offer(nodeIndex); while(!list.isEmpty()){ //获取索引 int index = (int)list.poll(); //获取节点 并打印 name值 System.out.println( graphNodes[index].getName()); for(int i = 0;i<curSize;i++){ if(!graphNodes[i].getVisted() && relation[index][i] == 1){ //如果该节点与index节点联通 获取 该节点 并把该节点置位访问过 GraphNode node = graphNodes[i]; node.setVisted(true); //入队列 list.offer(i); } } } } //深度优先搜索 利用栈 可以尝试使用LinkedList 或者自己实现栈结构 入栈 addFirst() 出栈 removeFirst() 获取 栈顶元素 getFirst() public void dfs(int nodeIndex){ LinkedList<Integer> list = new LinkedList(); //设置改图的第一个索引节点为 遍历 过后 的状态 graphNodes[nodeIndex].setVisted(true); //打印 其name 值 System.out.println(graphNodes[nodeIndex].getName()); //将该节点索引入栈 list.addFirst(nodeIndex); //当栈 不为空时候 一直循环 while(!list.isEmpty()){ //只是取出栈顶的index值 (并没有删除 节点) int index = list.getFirst();//调用 一个 获取 当前节点 的联通节点的索引 函数 获取 其中 一个 可用索引(即 并未 遍历过)//从这 我们 可以看出 list 维护的列表的大小 一层只是 一个 这就是深度搜索 优于 广度遍历 的地方 占用内存 少一点 int j = getNextAdjNodeIndex(index); //如果 获取 到 索引 那么 对应节点 置为 访问过 并且 打印 入栈,否则 出栈 (后续再 继续 循环 回溯) if(j!= -1){ graphNodes[j].setVisted(true); System.out.println(graphNodes[j].getName()); list.addFirst(j); }else{ list.removeFirst(); } } } //通过索引p来获取 邻接矩阵中与该 节点联通 的 节点索引 private int getNextAdjNodeIndex(int p) { for(int i=0; i<curSize;i++){ if(!graphNodes[i].getVisted() && relation[p][i] == 1){ return i; } } return -1; } public void printMatrx(){ for(int[] arr: relation){ System.out.println(); for(int i:arr){ System.out.print(i); } } }}class GraphNode{ private String name; private boolean visted; public GraphNode(String name) { this.name = name; this.visted = false; } public String getName() { return name; } public void setName(String name) { this.name = name; } public boolean getVisted() { return visted; } public void setVisted(boolean visted) { this.visted = visted; }}
阅读全文
0 0
- 深度优先遍历 广度优先遍历JAVA
- 广度优先遍历和深度优先遍历
- 深度优先遍历与广度优先遍历
- 深度优先遍历和广度优先遍历
- 深度优先遍历与广度优先遍历
- 深度优先遍历 和 广度优先遍历
- 深度优先遍历与广度优先遍历
- 深度优先遍历与广度优先遍历
- 深度优先遍历与广度优先遍历
- 深度优先遍历和广度优先遍历
- 深度优先遍历和广度优先遍历
- 深度优先遍历与广度优先遍历
- 深度优先遍历与广度优先遍历
- 深度优先遍历,广度优先遍历
- 深度优先遍历和广度优先遍历
- 深度优先遍历和广度优先遍历
- 深度优先遍历和广度优先遍历
- java广度优先遍历
- 图文详解MyEclipse中新建Maven webapp项目的步骤(很详细)
- 理解zookeeper选举机制
- CodeForces 893B Beautiful Divisors
- <4>C++ Primer 变量
- ubuntu下ping www.baidu.com 出错误
- 深度优先遍历 广度优先遍历JAVA
- Zookeeper安装过程中的坑
- Laravel-admin之修改操作日志
- 服务器环境搭建
- 项目中最近遇到的一些bug
- KMP算法的实现及优化
- GCC 版本下载地址,这里比较全,gcc版本一定要对应,不然就会各种不兼容依赖,把人折腾疯了
- Vue.js实战笔记Day1(vue-cli)
- 【Android】【Dagger】Dagger2 依赖注入