下图右边就是左边的树的morris序
只要一个节点有左树,该节点一定会到达两次.
后序
public class Code_MorrisTraversal {
public static class Node{
public int value;
Node left;
Node right;
public Node(int data){
this.value = data;
}
}
/*
* 4
* 2 6
* 1 3 5 7
*
*/
public static void main(String[] args) {
Node head = new Node(4);
head.left = new Node(2);
head.right = new Node(6);
head.left.left = new Node(1);
head.left.right = new Node(3);
head.right.left = new Node(5);
head.right.right = new Node(7);
morrisPre(head);
morrisIn(head);
morrisPos(head);
}
public static void process(Node node){
if(null == node){
return;
}
// 1
process(node.left);
// 2
process(node.right);
// 3
}
public static void morris(Node head){
if(null == head){
return;
}
Node cur = head;
Node mostRight = null;
while(cur != null){
mostRight = cur.left;
if(null != mostRight){// 如果有左子树
while (null != mostRight.right && mostRight.right != cur){
mostRight = mostRight.right;
}
// cur左树上最右节点
if(null == mostRight.right){
mostRight.right = cur;
cur = cur.left;
continue;
}else{
mostRight.right = null;
}
}
cur = cur.right;
}
}
// 先序遍历
public static void morrisPre(Node head){
if(null == head){
return;
}
Node cur = head;
Node mostRight = null;
while(cur != null){
mostRight = cur.left;
if(null != mostRight){// 如果有左子树
while (null != mostRight.right && mostRight.right != cur){
mostRight = mostRight.right;
}
// cur左树上最右节点
if(null == mostRight.right){
System.out.println(cur.value); // 第一次碰到该节点,打印该节点
mostRight.right = cur;
cur = cur.left;
continue;
}else{
mostRight.right = null;
}
}else{
System.out.println(cur.value);
}
cur = cur.right;
}
}
// 中序遍历
public static void morrisIn(Node head){
if(null == head){
return;
}
Node cur = head;
Node mostRight = null;
while(cur != null){
mostRight = cur.left;
if(null != mostRight){// 如果有左子树
while (null != mostRight.right && mostRight.right != cur){
mostRight = mostRight.right;
}
// cur左树上最右节点
if(null == mostRight.right){
mostRight.right = cur;
cur = cur.left;
continue;
}else{
mostRight.right = null;
}
}
System.out.println(cur.value);
cur = cur.right;
}
}
// 后序遍历
public static void morrisPos(Node head){
if(null == head){
return;
}
Node cur = head;
Node mostRight = null;
while(cur != null){
mostRight = cur.left;
if(null != mostRight){// 如果有左子树
while (null != mostRight.right && mostRight.right != cur){
mostRight = mostRight.right;
}
// cur左树上最右节点
if(null == mostRight.right){
mostRight.right = cur;
cur = cur.left;
continue;
}else{
mostRight.right = null;
printEdge(cur.left); // 该节点的左子数的右节点逆序
}
}
cur = cur.right;
}
printEdge(head); // 头节点的右节点逆序
}
public static void printEdge(Node node){
Node tail = reverseEdge(node);
Node cur = tail;
while(null != cur){
System.out.println(cur.value+" ");
cur = cur.right;
}
reverseEdge(tail);
}
public static Node reverseEdge(Node from){
Node pre = null;
Node next = null;
while(from != null){
next = from.right;
from.right = pre;
pre = from;
from = next;
}
return pre;
}
}