二叉树求子树Java实现

在准备Amazon的面试,有一道题目是这样的。

已知两个树A,B,求B是否是A的子树。



其实题目并不难。不知道为什么我就把自己困在建树上了。我记得我上一次写二叉树也是把自己困在建树上了。其实遍历什么的都很清晰。我也不记得我两年前是怎么建树的了,这次重新写了一个。

不知道在哪里看的实例输入里面有0,从此0在我脑海里面根深蒂固。我的输入还蛮奇怪的。仔细想想其实还是不把0纳入考虑,因为会影响结果。不过懒得改了。。。建树建成我这样也是。。。

先看重点的好了,参考了网上现有的很多博客。我已经不记得当时看到的是哪个了。

思路很清晰:

	public boolean HasSubTree(Node root1, Node root2) {
		// TODO Auto-generated method stub
		boolean result = false;
		if(root1 != null && root2 != null)//排除特殊根不存在的特殊情况
		{
			if(root1.val == root2.val)//如果两个根一样,测试
			{
				result = DoesTree1HasTree2(root1,root2);
			}
		}
		if(result!=true)
		{
			result = DoesTree1HasTree2(root1.left,root2);
		}
		if(result!=true)
		{
			result = DoesTree1HasTree2(root1.right,root2);
		}
		
		return result;
	}

	private boolean DoesTree1HasTree2(Node root1, Node root2) {
		// TODO Auto-generated method stub
		boolean lflag = false;
		boolean rflag = false;
		
		if(root2 == null)
			return true;//测试到树B结尾了,搞定
		
		if(root1 == null)
			return false;//测到树A结尾了,没有办法继续,B一定不是A子树
		
		if(root1.val != root2.val)
		{
			return false;//最后不同
		}else
		{
			lflag = DoesTree1HasTree2(root1.left,root2.left);
			rflag = DoesTree1HasTree2(root1.right, root2.right);
			
			return lflag&&rflag;
		}
	}
主函数:

package Tree;

import Tree.BinaryTree.Node;

public class HasSubtree {
	/*
	 * 输入两棵树A和B,判断B是不是A的子树
	 */
	
	public static void main(String[] args){
		
		System.out.println("============================= Tree 1 ==========================================");
		/*
		 *         1
		 *      /     \
		 *     2       3
		 *   /  \     /  \
		 *  4    5   0    6
		 * / \  / \
		 * 0  0	7 0
		       /\
		      0 0
		 */
		int[] data01 = {1,2,4,0,0,5,7,0,0,0,3,0,6};
		BinaryTree bTree = new BinaryTree();		
		bTree.root = bTree.buildTree(bTree.root,data01);
		bTree.PreOrderTraverse(bTree.root);
		
		System.out.println("============================= Tree 2 ==========================================");
		int[] data02 = {2,4,0,0,5};
		BinaryTree bTree2 = new BinaryTree();		
		bTree2.root = bTree2.buildTree(bTree2.root,data02);		
		bTree2.PreOrderTraverse(bTree2.root);
		
		boolean flag = false;
		flag = bTree.HasSubTree(bTree.root,bTree2.root);
		System.out.println("=======================================\n"+flag);

		
	}



}

二叉树部分:

package Tree;

import java.util.Stack;

import Tree.BinaryTree.Node;

public class BinaryTree {

	Node root;
	Node parent = null;
	
	public static class Node{
		int val;
		Node left;
		Node right;
		
		public Node(int val)
		{
			this.left = null;
			this.right = null;
			this.val = val;
		}
	}
	
	public BinaryTree()
	{
		root = null;
	}

	public Node buildTree(Node root, int[] data) {
		// TODO Auto-generated method stub
		int i=0;
		Node nowNode= null;
		Node LastNode = null;
		if(root == null)
			{
				root = new Node(data[i]);
				nowNode = root;
				LastNode = root;
				i++;
			}		
		
		while(i < data.length)
		{
//			System.out.println("while:   i:"+i+" 要存入的是: "+data[i]+" 叶子节点是: "+nowNode.val);
			if(nowNode.val == 0)
			{
				
				if(LastNode.right == null)
				{
					Node node = new Node(data[i]);
					LastNode.right = node;
					nowNode = LastNode.right;
					i++;
					parent = null;
					nowNode = FindParentsNode(root,LastNode);
				}else
				{
//					System.out.println("Last: "+LastNode.val +"\tNow : "+nowNode.val);
					while(nowNode!=null)
					{
						parent = null;
						
						if(nowNode.right!=null)
						{
							LastNode = nowNode;
							parent = null;
							nowNode = FindParentsNode(root,LastNode);

						}else
						{
//							System.out.println("Out of Bounds:\t"+i);
							Node node = new Node(data[i]);
							LastNode = nowNode;
							nowNode.right = node;
							nowNode = nowNode.right;
							i++;
							break;

						}
					}
					
					
					
				}
			}else
			{
				if(nowNode.left == null)
				{
//					
						Node node = new Node(data[i]);
						nowNode.left = node;
						LastNode = nowNode;
						nowNode = nowNode.left;
//						System.out.println("i:"+i+"要存入的是: "+data[i]+" 叶子节点是: "+nowNode.val);
						i++;
					} 	
				else
				{
					Node node = new Node(data[i]);
					nowNode.right = node;
					LastNode = nowNode;
					nowNode =nowNode.right;
					i++;
				}
			}

			}
		return root;
		

		
	}

	private Node FindParentsNode(Node root2, Node node) {
		// TODO Auto-generated method stub
		Node p = root2;
		
		if(p != null)
		{
//			System.out.println(p.val);
			if(p.left!=null)
			if(p.left.val == node.val)
				parent = p;
			if(p.right!=null)
			if(p.right.val == node.val)
				parent = p;
				
			FindParentsNode(p.left,node);
			FindParentsNode(p.right,node);
		}else
			return parent;
		return parent;
	}
	
	void PreOrderTraverse(Node root) {
		// TODO Auto-generated method stub
		Node p = root;
		if(p != null)
		{
			System.out.println(p.val);
			PreOrderTraverse(p.left);
			PreOrderTraverse(p.right);
		}else
			return;
		
	}

	public boolean HasSubTree(Node root1, Node root2) {
		// TODO Auto-generated method stub
		boolean result = false;
		if(root1 != null && root2 != null)
		{
			if(root1.val == root2.val)
			{
				result = DoesTree1HasTree2(root1,root2);
			}
		}
		if(result!=true)
		{
			result = DoesTree1HasTree2(root1.left,root2);
		}
		if(result!=true)
		{
			result = DoesTree1HasTree2(root1.right,root2);
		}
		
		return result;
	}

	private boolean DoesTree1HasTree2(Node root1, Node root2) {
		// TODO Auto-generated method stub
		boolean lflag = false;
		boolean rflag = false;
		
		if(root2 == null)
			return true;//测试到树B结尾了,搞定
		
		if(root1 == null)
			return false;//测到树A结尾了,没有办法继续,B一定不是A子树
		
		if(root1.val != root2.val)
		{
			return false;//最后不同
		}else
		{
			lflag = DoesTree1HasTree2(root1.left,root2.left);
			rflag = DoesTree1HasTree2(root1.right, root2.right);
			
			return lflag&&rflag;
		}
	}
	
	
}




  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值