自学内容网 自学内容网

每日一刷——二叉树——12.09

第一题:二叉树的层序遍历

题目描述:102. 二叉树的层序遍历 - 力扣(LeetCode)

我的思路:

拿到这个题目,我首先想到的是利用队列来模拟,给我二叉树的根节点,然后我来返回每一层的各个节点,但是为啥我甚至觉得这个题目给的输入就是按照层序遍历来给的呢??

然后感觉还有一个点就是咋返回成几个list嵌套

===>二叉树题目就是培养递归思维的

题目分析:

由于先进先出,取出一个节点之后,就再往里边添加它自己的左右孩子,这样左右孩子的顺序还是在本层节点的后边,但是在下一层其他节点的前面 

===》1.怎么返回成几个list嵌套?那就每一层安排一个list,这个完了之后就添加到答案数组中,

===》2.怎么知道这一层有多少个数字?  其实就是上一层执行了往队列里边添加数字了之后,它自己就走了,上一层的数字都走了之后,就可以发现此时,队列里边就是下一层即将要执行的数字,所以就定义一个count变量,将count=queue.size()

笑死,每次都感觉自己的思维能力不够,哎,还要多模仿多练习啊.....

知识点回顾:

1.List

在获得List对象之后,就可以对其进行元素的添加、删除、修改和查询等操作了。下面是一些常用的List元素操作方法:

===>添加元素:

向List集合中添加元素,我们可以使用add()方法、addAll()方法和ListIterator的add()方法。这些方法分别具有以下特点:

    add()方法:将指定元素添加到List的末尾;
    addAll()方法:将指定集合中的所有元素添加到List的末尾;
    ListIterator的add()方法:将指定元素插入到ListIterator当前位置。

2.queue

当使用LinkedList时:

import java.util.LinkedList;
import java.util.Queue;

public class LinkedListExample {
    public static void main(String[] args) {
        Queue<Integer> queue = new LinkedList<>();

        // 向队列添加元素
        queue.add(1);
        queue.add(2);

        // 使用poll和peek方法
        System.out.println(queue.poll()); // 输出: 1
        System.out.println(queue.peek());  // 输出: 2
    }
}

1.E poll(): 移除并返回队列头部的元素,如果没有元素则返回null

2.E peek(): 返回队列头部的元素但不移除它,如果没有元素则返回null。

题解:

/**
 * Definition for a binary tree node.
 * public class TreeNode {
 *     int val;
 *     TreeNode left;
 *     TreeNode right;
 *     TreeNode() {}
 *     TreeNode(int val) { this.val = val; }
 *     TreeNode(int val, TreeNode left, TreeNode right) {
 *         this.val = val;
 *         this.left = left;
 *         this.right = right;
 *     }
 * }
 */
class Solution {
    public List<List<Integer>> levelOrder(TreeNode root) {
        List<List<Integer>> ans =new ArrayList<>();
        Queue<TreeNode> queue =new LinkedList<>();
        queue.add(root);
        if(root == null)
            return ans;
        else{    //可是这个应该是需要记录每一行究竟有多少个吧
            while(!queue.isEmpty()){
                int count =queue.size();
                //要用两个数组
                List<Integer> list =new ArrayList<>();
                while(count >0){
                    TreeNode temp =queue.poll();
                    list.add(temp.val);
                    if(temp.left!=null)
                        queue.add(temp.left);
                    if(temp.right!=null){
                        queue.add(temp.right);
                    }
                    count--;
                }
                ans.add(list);
            }
            return ans;
        }
    }
}

第二题:二叉树的最大深度

题目描述:104. 二叉树的最大深度 - 力扣(LeetCode)

我的思路:

感觉是深度优先遍历,用一个栈?

好吧,感觉根本不需要用到栈,因为用栈是可以储存节点,这样便于我们把节点打印出来,现在我们并不需要打印,所以也就没什么必要用到栈,好吧。

呜呜呜

题目分析:

这个题目的思路就是:

用一个外部的变量来定义每一条路上的深度,然后求一下最大值,

知识点回顾:

1.stack的常见用法:

我的题解:

/**
 * Definition for a binary tree node.
 * public class TreeNode {
 *     int val;
 *     TreeNode left;
 *     TreeNode right;
 *     TreeNode() {}
 *     TreeNode(int val) { this.val = val; }
 *     TreeNode(int val, TreeNode left, TreeNode right) {
 *         this.val = val;
 *         this.left = left;
 *         this.right = right;
 *     }
 * }
 */
class Solution {
    public int maxDepth(TreeNode root) {
        if(root==null)
            return 0;
        //这里是往下边递归,然后发现有没有最大值
        else{
            return traverse(root);
        }
    }

    public static int depth=0;
    //往下遍历
    public static int traverse(TreeNode node){
        depth++;
        while(node!=null){
            traverse(node.left);
            traverse(node.right);
        }
    }
}
改进上一次的代码:

1.要用一个depth求每一条路的最大深度,

还要用一个res记录目前的最大深度

2.那么res什么时候使用,就是当判断到自己什么时候是空了,自己空了,就更新这个值

3.然后就是在递归遍历左边和右边中间或者两旁的一些代码,就是用来思考这个节点的前序时应该做什么操作,后序做什么操作,中序做什么操作

4.这里又忘记返回了,这里为啥要返回呢?  因为到达了末端了,下边的代码只有往下走的功能,到达尽头了还不回头,就要时间超出限制了。

 if(node==null){
            res=Math.max(res,depth);
            return;   
时间超时了哈,栓Q 
/**
 * Definition for a binary tree node.
 * public class TreeNode {
 *     int val;
 *     TreeNode left;
 *     TreeNode right;
 *     TreeNode() {}
 *     TreeNode(int val) { this.val = val; }
 *     TreeNode(int val, TreeNode left, TreeNode right) {
 *         this.val = val;
 *         this.left = left;
 *         this.right = right;
 *     }
 * }
 */
class Solution {
    public int maxDepth(TreeNode root) {
        if(root==null)
            return 0;
        //这里是往下边递归,然后发现有没有最大值
        else{
            traverse(root);
            return res;
        }
    }

    public static int depth=0;
    public static int res=0;   //存放每一条路上的最大值
    //往下遍历
    public static void traverse(TreeNode node){
        if(node==null){
            res=Math.max(res,depth);
            return;   //这里又忘记返回了,这里为啥要返回呢?  因为到达了末端了,下边的代码只有往下走的功能,到达尽头了还不回头,就要时间超出限制了
        }
        while(node!=null){
            depth++;
            traverse(node.left);
            traverse(node.right);
            depth--;
            //把它想象成一个指针
        }
    }
}

感觉自己的思路很乱,就是不知道从何开始想这个题目,然后很多思路糅合在一起,像一团乱码 

正确题解:

没事,我们还有一种思路哈,惹惹

/**
 * Definition for a binary tree node.
 * public class TreeNode {
 *     int val;
 *     TreeNode left;
 *     TreeNode right;
 *     TreeNode() {}
 *     TreeNode(int val) { this.val = val; }
 *     TreeNode(int val, TreeNode left, TreeNode right) {
 *         this.val = val;
 *         this.left = left;
 *         this.right = right;
 *     }
 * }
 */
class Solution {
    public int maxDepth(TreeNode root) {
       if(root ==null)
            return 0;
        int leftMax =maxDepth(root.left);
        int rightMax =maxDepth(root.right);
        int res =Math.max(leftMax,rightMax) +1;

        return res;
    }
}

往下不断递归,上一层应该是下边两层里边的最大值的深度+1,也就是说这个int的位置放在,左右都求完深度之后,又回到了自己这里,然后深度+1 

第三题:二叉树的锯齿形层序遍历

题目描述:103. 二叉树的锯齿形层序遍历 - 力扣(LeetCode)

题目分析:

其实和第一题很类似,但是要用双端队列写,然后添加一个flag,用于控制此时的方向

题解:

/**
 * Definition for a binary tree node.
 * public class TreeNode {
 *     int val;
 *     TreeNode left;
 *     TreeNode right;
 *     TreeNode() {}
 *     TreeNode(int val) { this.val = val; }
 *     TreeNode(int val, TreeNode left, TreeNode right) {
 *         this.val = val;
 *         this.left = left;
 *         this.right = right;
 *     }
 * }
 */
class Solution {
    public List<List<Integer>> zigzagLevelOrder(TreeNode root) {
        List<List<Integer>> ans =new ArrayList<>();
        if(root==null){
            return ans;
        }
        LinkedList<TreeNode> deque =new LinkedList<>();  //双端队列
        deque.add(root); //先把头节点放进去
        int size=0;
        boolean isHead =true ;//用来控制锯齿的顺序
        while(!deque.isEmpty()){
            size =deque.size();//先得到size
            List<Integer> curLevel = new ArrayList<>();
            for(int i =0;i<size;i++){  //搞size次
                TreeNode cur =isHead ? deque.pollFirst() :deque.pollLast();
                curLevel.add(cur.val);
                if(isHead){
                    if(cur.left !=null){
                        deque.addLast(cur.left);
                    }
                    if(cur.right!=null){
                        deque.addLast(cur.right);
                    }
                }else{
                    if(cur.right!=null){
                        deque.addFirst(cur.right);
                    }
                    if(cur.left !=null){
                        deque.addFirst(cur.left);
                    }
                }
            }
            ans.add(curLevel);
            isHead =!isHead;

        }
        return ans;
    }
}

没办法,多练习吧


原文地址:https://blog.csdn.net/2301_80073593/article/details/144359928

免责声明:本站文章内容转载自网络资源,如本站内容侵犯了原著者的合法权益,可联系本站删除。更多内容请关注自学内容网(zxcms.com)!