二叉树练习题

1.相同的树

. - 力扣(LeetCode)

给你两棵二叉树的根节点 p 和 q ,编写一个函数来检验这两棵树是否相同。

如果两个树在结构上相同,并且节点具有相同的值,则认为它们是相同的。

class Solution {
    public boolean isSameTree(TreeNode p, TreeNode q) {
if(p==null&&q!=null||p!=null&&q==null){
    return false;
}
if(p==null&&q==null){
    return true;
}
if(p.val!=q.val){
    return false;
}
return isSameTree(p.left,q.left)&&isSameTree(p.right,q.right);
    }
}

2.另一棵树的子树

. - 力扣(LeetCode)

给你两棵二叉树 root 和 subRoot 。检验 root 中是否包含和 subRoot 具有相同结构和节点值的子树。如果存在,返回 true ;否则,返回 false 。

二叉树 tree 的一棵子树包括 tree 的某个节点和这个节点的所有后代节点。tree 也可以看做它自身的一棵子树。

                                 

class Solution {
    public boolean isSubtree(TreeNode root, TreeNode subRoot) {
if(root==null){
    return false;
}
…}
if(p==null&&q==null){
    return true;
}
if(p.val!=q.val){ 
    return false;
}
return isSameTree(p.left,q.left)&&isSameTree(p.right,q.right);
    }
}

3.翻转二叉树

. - 力扣(LeetCode)

给你一棵二叉树的根节点 root ,翻转这棵二叉树,并返回其根节点。

class Solution {
    public TreeNode invertTree(TreeNode root) {
if(root==null){
    return root;
}
TreeNode tmp=root.left;
root.left=root.right;
root.right=tmp;
invertTree(root.right);
invertTree(root.left);
return root;
    }
}

4. 判断一颗二叉树是否是平衡二叉树

. - 力扣(LeetCode)

给定一个二叉树,判断它是否是平衡二叉树

 方法一:

class Solution {
    public boolean isBalanced(TreeNode root) {
        if(root==null){
            return true;
        }
int left=getHigh(root.left);
int right=getHigh(root.right);
return Math.abs(left-right)<2&&isBalanced(root.left)&&isBalanced(root.right);
    }

public int getHigh(TreeNode root){
if(root==null){
    return 0;
}
int left=getHigh(root.left);
int right=getHigh(root.right);
int max=left>right?left:right;
return max+1;
}
}

方法2:

class Solution {
    public boolean isBalanced(TreeNode root) {
if(root==null){
    return true;
}
return gethight(root)>=0;
    }

public int gethight(TreeNode root){
if(root==null){
    return 0;
}
int left=gethight(root.left);
if(left<0){
    return -1;
}
int right=gethight(root.right);
if(right<0){
    return -1;
}
if(Math.abs(left-right)<2){
return Math.max(left,right)+1;
}
else{
    return -1;
}
}
}

5.对称二叉树

. - 力扣(LeetCode)

给你一个二叉树的根节点 root , 检查它是否轴对称。

 方法一:

class Solution {
    public boolean isSymmetric(TreeNode root) {
TreeNode tmp=cloneTree(root);
return isSameTree(root,invertTree(tmp));
    }

public TreeNode cloneTree(TreeNode root){
if(root==null){
    return null;
}
TreeNode node=new TreeNode(root.val);
node.left=cloneTree(root.left);
node.right=cloneTree(root.right);
return node;
}

public TreeNode invertTree(TreeNode root) {
if(root==null){
    return root;
}
TreeNode tmp=root.left;
root.left=root.right;
root.right=tmp;
invertTree(root.right);
invertTree(root.left);
return root;
    }
public boolean isSameTree(TreeNode p, TreeNode q) {
if(p==null&&q!=null||p!=null&&q==null){
    return false;
}
if(p==null&&q==null){
    return true;
}
if(p.val!=q.val){ 
    return false;
}
return isSameTree(p.left,q.left)&&isSameTree(p.right,q.right);
    }
}

方法二:

class Solution {
    public boolean isSymmetric(TreeNode root) {
if(root==null){
    return true;
}
return isSymmetricChild(root.left,root.right);
    }
public boolean isSymmetricChild(TreeNode left,TreeNode right){
if(left==null&&right!=null||left!=null&&right==null){
    return false;
}
if(right==null&&left==null){
    return true;
}
if(left.val!=right.val){
    return false;
}
return isSymmetricChild(left.left,right.right)&&isSymmetricChild(left.right,right.left);
}
}

6.二叉搜索树和双向链表

二叉搜索树与双向链表_牛客题霸_牛客网

输入一棵二叉搜索树,将该二叉搜索树转换成一个排序的双向链表。如下图所示

public class Solution {
    public TreeNode Convert(TreeNode pRootOfTree) {
      if(pRootOfTree==null) {
        return null;
      }
ConvertChild(pRootOfTree);

      TreeNode head=pRootOfTree;
while(head.left!=null){
    head=head.left;
}
return head;
    }
TreeNode prve=null;
    public void ConvertChild(TreeNode root){
if(root==null) return;
ConvertChild(root.left);
root.left=prve;
if(prve!=null){
    prve.right=root;
}
prve=root;
ConvertChild(root.right);
    }
}

7.二叉树的遍历

二叉树遍历_牛客题霸_牛客网

编一个程序,读入用户输入的一串先序遍历字符串,根据此字符串建立一个二叉树(以指针方式存储)。 例如如下的先序遍历字符串: ABC##DE#G##F### 其中“#”表示的是空格,空格字符代表空树。建立起此二叉树以后,再对二叉树进行中序遍历,输出遍历结果。

方法:

class TreeNode{
    public TreeNode left;
    public TreeNode right;
    public char val;

public TreeNode(char val){
    this.val=val;
}
}
// 注意类名必须为 Main, 不要有任何 package xxx 信息
public class Main {
    public static void main(String[] args) {
        Scanner in = new Scanner(System.in);
        // 注意 hasNext 和 hasNextLine 的区别
        while (in.hasNextLine()) { // 注意 while 处理多个 case
           String str=in.nextLine();

TreeNode root=creatTree(str);
inorderTree(root);
        }
    }
public static int i=0;
public static TreeNode creatTree(String str){
TreeNode root=null;
if(str.charAt(i)!='#'){
    root=new TreeNode(str.charAt(i));
    i++;
root.left=creatTree(str);
root.right=creatTree(str);
}else{
    i++;
}
return root;
}

public static void inorderTree(TreeNode root){
if(root==null){
    return;
}
inorderTree(root.left);
System.out.print(root.val+" ");
inorderTree(root.right);
}
}

8.二叉树的层序遍历

. - 力扣(LeetCode)

给你二叉树的根节点 root ,返回其节点值的 层序遍历 。 (即逐层地,从左到右访问所有节点)。

 方法:

class Solution {
    public List<List<Integer>> levelOrder(TreeNode root) {
Queue<TreeNode>queue=new LinkedList<>();
List<List<Integer>> res=new ArrayList<>();
if(root!=null){
queue.add(root);    
}
while(!queue.isEmpty()){
List<Integer>tmp=new ArrayList<>();
for(int i=queue.size();i>0;i--){
TreeNode node=queue.poll();
tmp.add(node.val);
if(node.left!=null) queue.add(node.left);
if(node.right!=null) queue.add(node.right);
}
res.add(tmp);
}
return res;
    }
}

9.二叉树的最近公共祖先

. - 力扣(LeetCode)

给定一个二叉树, 找到该树中两个指定节点的最近公共祖先。

 方法:

class Solution {
    public TreeNode lowestCommonAncestor(TreeNode root, TreeNode p, TreeNode q) {
        if(root==null){
            return null;
        }
if(root==p||root==q){
    return root;
}
TreeNode left=lowestCommonAncestor(root.left,p,q);
TreeNode right=lowestCommonAncestor(root.right,p,q);

if(left!=null&&right!=null){
    return root;
}
else if(left!=null){
    return left;
}
else{
    return right;
}
    }
}

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值