(三)資料結構樹之叉樹遍歷程式碼實現
阿新 • • 發佈:2019-02-19
二叉樹相關遍歷學習筆記
1:構建二叉樹資料結構
/**
* 樹節點資料結構
*/
public class TreeNode {
public int Index; public String data; public TreeNode leftTreeNode; public TreeNode rightTreeNode; public TreeNode(int index, String data) { this.Index = index; this.data = data; this.leftTreeNode = null; this.rightTreeNode = null; } } /** * 構造一個這種型別的二叉樹 * A * B C * D E F */ public void createBinaryTree() { TreeNode nodeB = new TreeNode(2, "B"); TreeNode nodeC = new TreeNode(3, "C"); TreeNode nodeD = new TreeNode(4, "D"); TreeNode nodeE = new TreeNode(5, "E"); TreeNode nodeF = new TreeNode(6, "F"); root.leftTreeNode = nodeB; root.rightTreeNode = nodeC; nodeC.leftTreeNode = nodeF; nodeB.leftTreeNode = nodeD; nodeB.rightTreeNode = nodeE; }
2:二叉樹的迭代遍歷
(1)前序遍歷
/**
* 遞迴式前序遍歷
*/
public void preOrder(TreeNode node) {
if (node == null) return; System.out.println("前序遍歷:" + node.data); preOrder(node.leftTreeNode); preOrder(node.rightTreeNode); } /** * 利用棧的實現前序遍歷 */ public void preStackOrder(TreeNode node) { if (node == null) return; Stack<TreeNode> stack = new Stack<TreeNode>(); stack.push(node); while (!stack.isEmpty()) { // 出棧和進棧 TreeNode n = stack.pop(); System.out.println("棧式前序遍歷:" + n.data); // 壓入子節點 if (n.rightTreeNode != null) { stack.push(n.rightTreeNode); } if (n.leftTreeNode != null) { stack.push(n.leftTreeNode); } } }
(2)中序遍歷
/** * 中序遍歷 */ public void midOrder(TreeNode node) { if (node == null) return; midOrder(node.leftTreeNode); System.out.println("中序遍歷:" + node.data); midOrder(node.rightTreeNode); } /** * 利用棧的實現中序遍歷 */ public void midStackOrder(TreeNode node) { if (node == null) return; Stack<TreeNode> stack = new Stack<TreeNode>(); TreeNode cur = node; while (cur != null || !stack.isEmpty()) { while (cur != null) { stack.push(cur); cur = cur.leftTreeNode; } cur = stack.pop(); System.out.println("棧式後序遍歷:" + cur.data); cur = cur.rightTreeNode; } }
(3)後序遍歷
/**
* 雙棧式後續序遍歷
*/
public void postStackOrder2(TreeNode node) {
if (node == null)
return;
Stack<TreeNode> stack = new Stack<TreeNode>();
Stack<TreeNode> modStack = new Stack<TreeNode>();//翻轉輸出用
stack.push(node);
while (!stack.isEmpty()) {
TreeNode cur = stack.pop();
modStack.push(cur);
if (cur.leftTreeNode != null) {
stack.push(cur.leftTreeNode);
}
if (cur.rightTreeNode != null) {
stack.push(cur.rightTreeNode);
}
}
while (!modStack.isEmpty()) {
System.out.println(modStack.pop().data + " ");
}
}
/**
* 雙棧式後續序遍歷
*/
public void postStackOrder2(TreeNode node) {
if (node == null)
return;
TreeNode cur = node;
Stack<TreeNode> stack = new Stack<TreeNode>();
while (node != null) {
// 左子樹入棧
for (; node.leftTreeNode != null; node = node.leftTreeNode)
stack.push(node);
// 當前節點無右子或右子已經輸出
while (node != null
&& (node.rightTreeNode == null || node.rightTreeNode == cur)) {
System.out.println(node.data + " ");
cur = node;// 記錄已輸出節點
if (stack.empty())
return;
node = stack.pop();
}
// 處理右子
stack.push(node);
node = node.rightTreeNode;
}
}
(4)層序遍歷
/**
* 層序遍歷,利用連結串列形式或者佇列的形式
* 樹的深度優先遍歷需要用–>棧;而廣度優先遍歷用–>佇列;
*/
public void levelListOrder(TreeNode node) {
if (node == null)
return;
LinkedList<TreeNode> queue = new LinkedList<TreeNode>();
queue.addFirst(node);
while (!queue.isEmpty()) {
TreeNode cur = queue.removeFirst();
System.out.print(cur.data + " ");
if (cur.leftTreeNode != null) {
queue.add(cur.leftTreeNode);
}
if (cur.rightTreeNode != null) {
queue.add(cur.rightTreeNode);
}
}
}