利用java实现二叉树以及非递归遍历算法

一,建立节点,包含数据、左二子、右儿子三部分

class Node {
	private Node lNode;
	private Node rNode;
	private char data;

	public Node() {

	}

	public Node(Node lNode, Node rNode, char data) {
		this.lNode = lNode;
		;
		this.rNode = rNode;
		this.data = data;
	}

	public char getChar() {
		return data;
	}

	public void setChar(char data) {
		this.data = data;
	}

	public Node get_lNode() {
		return lNode;
	}

	public Node get_rNode() {
		return rNode;
	}

	public void set_lNode(Node node) {
		this.lNode = node;
	}

	public void set_rNode(Node node) {
		this.rNode = node;
	}
}
2、创建二叉树类,具体实现过程代码里面有说明,这里是中序非递归遍历


public class binary_tree {
	Node root,temNode;//为根节点,指向不能移动,需要额外加一个Node去移动去动态增加节点
	Node[] nodes=new Node[4];
	char[] data;//接收输入的字符串,转化为字符数组
	int length;
	public binary_tree(){
		
	}
	//创造二叉树
	public  void creat(String string){
		data=string.toCharArray();
		int k=0,j=0,top=-1;//k表示加入的是左节点还是右节点,j为遍历字符数组,top
		while (j<data.length-1) {
			switch (data[j]){
			case '(':
				top++;
				nodes[top]=temNode;//top++后notes[top]指向刚建立的节点
				k=1;
				break;
			case ',':
				k=2;
				break;
			case ')':
				top--;//top--后notes[top]指向刚建立的节点上一个节点
				break;
			default:
				temNode=new Node(null,null,data[j]);//遇到第一个字母,构建新节点
				if (root==null) {//第一个字母,赋值给root;
					root=temNode;
				} else {
					switch (k) {
					case 1:
						nodes[top].set_lNode(temNode);
						break;

					case 2:
						nodes[top].set_rNode(temNode);
						break;
					}
				}
				
				break;
			
			
			}
			j++;	
		}
			
	}
	public int layout(){//返回的是二叉树的长度
		if (root!=null) {
			length=1;
			for (int j = 0; j < data.length; j++) {
				if (data[j]==')') {
					break;
				}else {
					if (data[j]=='(') {
						length++;
					}
				}
			}
			
			
		}
			
			
		return length;
	}
	//先序遍历
	public void preOreder(Node node) {
		if (node==null) {
			return;
		}else {
			System.out.println(node.getChar());
			preOreder(node.get_lNode());
			preOreder(node.get_rNode());
			
		}
	}
	//先序非递归遍历
	
	
	//核心思想在于,入栈的条件是它还有左儿子,当它左儿子左儿子左儿子全部入栈后,用T指向最后一个没有左儿子的节点,打印弹出,
	//然后另T指向它的右儿子,,然后重复;
	public void midNoRecursive(Node node){
		Node[] nodes=new Node[10];
		Node T=new Node();
		int top=-1;
		if (node!=null) {
			T=node;//把根元素存入栈,这里用数组代替栈
		}
		while(T!=null||top>-1){
			while (T!=null) {//此循环相当于将T节点入栈以及将其左儿子存入栈
				top++;
				nodes[top]=T;
				T=T.get_lNode();
			}
			if (top>-1) {//将T打印后弹出,
				T=nodes[top];
				top--;
				System.out.println(T.getChar()+"");
				T=T.get_rNode();
			}
		}
	}
	
}
3、最后验证

<span style="font-size:14px;">//二叉树的构建与遍历
public class test {

	public static void main(String[] args) {
		binary_tree bTree=new binary_tree();
		bTree.creat("A(B(D(M,G)),C(E,F))");
		bTree.preOreder(bTree.root);//顺序遍历
		bTree.midNoRecursive(bTree.root);//中序非递归遍历
		System.out.println(bTree.layout());
	}

}</span>

二、在这里增加一个层序遍历,里面利用的是队列,获得一个根节点,存入队列,然后弹出打印,并将它的左右节点都存进去,然后在弹出一个,在将其左右儿子存进去,不断循环,直到队列为空

1、构造自己的队列,里面有三个方法,加入,移除与判断是否为空

public class Queue {
	private int default_size=10;
	private int front=0;
	private int real=0;
	
	private Node[] element;
	
	public Queue() {
		element=new Node[default_size];
	}
	public Queue(int size){
		default_size=size;
		element=new Node[default_size];
	}
	
	public void add(Node node){
		
			element[real++]=node;
		
	}
	public Node remove() {
		Node object=element[front];
		element[front]=null;
		front++;
		return object;
		
	}
	public boolean isEmpty(){
		return front==real;
	}
}
2、放在二叉树里的层序遍历方法,记住队列里放的元素为Node,最开始放进去的是根元素root

public static void LevelOrderTracersal(Binary_tree tree) {
		Queue queue=new Queue();
		Binary_tree T=new Binary_tree();
		if (tree==null) {
			return;
		}else {
			queue.add(tree.root);	
		}
		while(!queue.isEmpty()){
			T.root=queue.remove();
			System.out.println(T.root.getChar());
			if (T.root.get_lNode()!=null) {
				queue.add(T.root.get_lNode());
			}
			if (T.root.get_rNode()!=null) {
				queue.add(T.root.get_rNode());
			}
		}
	}





评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值