递归与非递归实现二叉树的序列化与反序列化

序列化

递归法

思路

如果子节点为空,用null表示。如果不用null表示会无法确定位置!
序列化的时候和遍历的时候差不多,也是用递归。这里只写一种方法,因为前序,中序,后序只不过是顺序不一样而已,调换一下ans.add的顺序即可。

代码

public static Queue<String> preSerial(Node head){
	Queue<String>ans=new LinkedList<>();
	pres(head,ans);
	return ans;
}
public static void pres(Node head,Queue<String>ans) {
	if(head==null) {
		ans.add(null);
	}else {
		ans.add(String.valueOf(head.val));
		pres(head.left,ans);
		pres(head.right,ans);
	}
}

非递归法

思路

思路是用bfs的思想。
我们使用队列queue保存节点,使用ans保存序列化。首先头节点若为空就只序列化,如果不为空就再入队。然后判断子节点,先判断左子节点,为空就只入队不序列化,不为空就都加,然后判断右子节点,最后循环完要poll给head。如此反复判断直至队列为空.

代码

```//非递归序列化
public static Queue<String> levelSerial(Node head){
	Queue<String>ans=new LinkedList<>();
	if(head==null) {
		ans.add(null);
	}else {
		ans.add(String.valueOf(head.val));
		Queue<Node>queue=new LinkedList<>();
		queue.add(head);
		while(!queue.isEmpty()) {
			head=queue.poll();
			if(head==null) continue;
			if(head.left!=null) {
				ans.add(String.valueOf(head.left.val));
				queue.add(head.left);
			}else {
				queue.add(null);
			}
			if(head.right!=null) {
				ans.add(String.valueOf(head.right.val));
				queue.add(head.right);
			}else {
				ans.add(null);
			}
		}
	}
	return ans;
}

反序列化

递归法

思路

建立二叉树的顺序也和序列化保持一致。

代码

public static Node buildByPreQueue(Queue<String> prelist) {
	if(prelist==null||prelist.size()==0) {
		return null;
	}
	return preb(prelist);
}
public static Node preb(Queue<String> prelist) {
	String value=prelist.poll();
	if(value==null) {
		return null;
	}
	Node head=new Node(Integer.valueOf(value));
	head.left=preb(prelist);
	head.right=preb(prelist);
	return head;
}

非递归法

思路

bfs按层建立节点

代码

//非递归反序列化
public static Node buildByLevelQueue(Queue<String> levelList) {
	if(levelList==null||levelList.size()==0) {
		return null;
	}
	Node head = generateNode(levelList.poll());
	Queue<Node> queue=new LinkedList<>();
	if(head!=null) {
		queue.add(head);
	}
	Node node=null;
	while(!queue.isEmpty()) {
		node=queue.poll();
		node.left=generateNode(levelList.poll());
		node.right=generateNode(levelList.poll());
		if(node.left!=null) {
			queue.add(node.left);
		}
		if(node.right!=null) {
			queue.add(node.right);
		}
	}
	return head;
}
public static Node generateNode(String val) {
	if(val==null) {
		return null;
	}
	return new Node(Integer.valueOf(val));
}

注意点以及别的

  • 序列化与反序列化是严格对应的! 意思就是如果使用前序序列化,那么就必须使用前序反序列化建立节点,这个是严格对应的,否则会出现错误!还有,中序遍历不能够序列化,因为可能会出现歧义。
  • 朋友可以想一下,其实bfs按层遍历(从上到下,从左到右)其实就是先序遍历,不论是打印还是序列化反序列化,都是相通的。

说实话,理解的还不是很透彻,最多只能理解一些,但是自己写应该写不出,以后多看看、

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值