LeetCodeHot100|对称二叉树、二叉树的直径、二叉树的层序遍历

对称二叉树

给你一个二叉树的根节点,判断它是否对称

输入: root = 1,2,2,3,4,4,3

输出: true

思路分析

使用递归来解题,因为是求对称,所以判断的时候需要满足两个点,第一个点就是任意根节点的左子树等于右子树,具有相同的值。第二个点就是镜像对称。

具体可以使用递归函数,通过同步移动两个指针的方法来遍历这颗树,p指针和q指针一开始都指向这颗树的根,随后p左移的时候p右移,p右移的时候q左移,每次检查当前p和q节点的值是否相等,如果相等再判断左右子树是否对称。

代码解读

cpp 复制代码
/**

 * Definition for a binary tree node.

 * struct TreeNode {

 *     int val;

 *     TreeNode *left;

 *     TreeNode *right;

 *     TreeNode() : val(0), left(nullptr), right(nullptr) {}

 *     TreeNode(int x) : val(x), left(nullptr), right(nullptr) {}

 *     TreeNode(int x, TreeNode *left, TreeNode *right) : val(x), left(left), right(right) {}

 * };

 */

class Solution {

public:

    bool isSymmetric(TreeNode* root) {

        // 1.检查是否轴对称

        // 既然要检测树,那么如何去找左右节点呢?-> 使用指针移动

        return root == nullptr || recur(root -> left, root -> right);

    }

/**

终止条件 L 和 R 同时越过叶节点,此树从顶至底的节点都对称,

*/

private:

    bool recur(TreeNode* L, TreeNode* R) {  

        if (L == nullptr && R ==nullptr) return true;

        if(L == nullptr || R == nullptr || L -> val != R ->val) return false;

        return recur(L -> left, R -> right) && recur(L->right, R->left);

  

    }

};

二叉树的直径

给你一颗二叉树的根节点,返回该树的直径

二叉树的直径是指树中任意两个节点之间最长路径的长度。这条路径可能经过也可能不经过根节点root,两节点之间路径的长度由它们之间的边数表示。

解题思路

首先需要知道求直径相当于求什么。一条路径的长度为该路径经过的节点数减一,所以求直径等效于求路径经过节点数的最大值减一。比如4到1就是三个节点,减去一个节点就是2.

而任意一个路径都可以被看作是某一个节点为起点,从其左儿子和右儿子向下便利的路径拼接得到。

假设我们知道对于该节点的左儿子向下便利经过最多的节点数L和其右儿子向下便利经过节点R,那么以该节点为起点的路径经过节点数最大值为 L+R+1.

cpp 复制代码
class Solution { 
	int ans; // 全局变量: 记录二叉树中 最长路径的节点总数
	
	// 定义一个递归函数: 计算以rt为根的子树的最大深度
	int depth(TreeNode* rt) { 
		// 递归终止条件: 空节点深度为 0
		if(rt == NULL) { 
			return 0;
		}
		
		// 后序便利: 先计算左子树的深度L
		int L = depth(rt -> left);
		// 再计算右子树深度 R
		int R = depth(rt -> right);
		
		// 核心: 当前节点的路径长度 = 左深度 + 右深度  +1 
		ans = max(ans, L + R + 1); // 这里是更新当前的全局最大值
		
		return max(L,R)  +1;
		
	}
public:
	// 主函数:求二叉树的直径
	int diameterOfBinaryTree(TreeNode* root) { 
		// 初始化:最少一个节点
		ans = 1;
		// 递归便利整颗树, 计算所以节点的路径
		depth(root);
		// 直接 = 最长路径节点数 - 1
		return ans - 1;
	}
}

102.二叉树的层序遍历

给你二叉树的根节点root,返回其节点值的层序遍历。

**输入:root = 3,9,20,null,null,15,7

输出:\[\[3,9,20,15,7]

思路分析

首先题目要求是按层打印,又被称为二叉树的广度优先搜索BFS. 而BFS是借助队列的先入先出的特性来实现的。

cpp 复制代码
/**

 * Definition for a binary tree node.

 * struct TreeNode {

 *     int val;

 *     TreeNode *left;

 *     TreeNode *right;

 *     TreeNode() : val(0), left(nullptr), right(nullptr) {}

 *     TreeNode(int x) : val(x), left(nullptr), right(nullptr) {}

 *     TreeNode(int x, TreeNode *left, TreeNode *right) : val(x), left(left), right(right) {}

 * };

 */

class Solution {

public:
	// 二叉树层序便利,返回二维数组,每一层对应一个一维数组
    vector<vector<int>> levelOrder(TreeNode* root) {
		// 队列,用于BFS, 存储节点指针, 利用先进先出实现层序
		queue<TreeNode*> que;
		// 用于存放最终结果;每一层一组节点值
		vector<vector<int>> res;
		// 如果根节点非空,先将根节点入队
        if(root != nullptr) que.push(root);
		// 队列不为空,说明还有节点未遍历
        while(!que.empty()) {
			// 临时数组,存放当前这一层的所有节点值
            vector<int> tmp;
			// 关键: 只循环当前层的节点个数
            for(int i = que.size();i > 0; --i) {
				// 取出队首节点
                root = que.front(); // 取出首队列和弹出首队列
				// 谈出队首节点
                que.pop();
				// 将节点值加入当前层数组
                tmp.push_back(root-> val);
				// 左孩子不为空则入队,作为下一层节点
                if( root -> left != nullptr) que.push(root -> left);
				
                if (root -> right != nullptr) que.push(root -> right);

            }
			// 当前层便利完毕,这一层结果加入最终结果
            res.push_back(tmp);

        }

        return res;

    }

};
相关推荐
GG-_-Bond8 小时前
9.1 kv存储resp协议模拟面试
c++
米糕闯编程9 小时前
鱼香ros2(五)用C++编写节点
c++·ros2·cmakelists·鱼香
xiangyun6110 小时前
【408数据结构 08】队列:循环队列判空判满,408年年考,一次讲清
c语言·开发语言·数据结构·c++·算法
xiangyun6110 小时前
【408数据结构 06】双链表、循环链表、静态链表
c语言·开发语言·数据结构·c++·算法
OKkankan11 小时前
LangChain 能力详解!:输出解析、RAG、向量数据库与 Retriever 检索器
数据结构·python·langchain·ai应用
蓝速科技11 小时前
便民服务大厅 AI 数字人一体机场景适配与落地指南丨蓝速科技
大数据·网络·数据结构·人工智能·自然语言处理·数据分析·运维开发
fpcc12 小时前
计算机原理—构建过程中的分段分析
c++
xxwxx__12 小时前
C++ AVL 树深度剖析:平衡二叉搜索树原理、源码与面试考点
数据结构·c++
Logic10112 小时前
C语言/数据结构数组题解:数字列表加一(Plus One)——进位处理与数组扩展
c语言·数据结构·模拟·数组·时间复杂度·算法题·进位
Escalating_xu12 小时前
【C语言常见概念】从第一行代码到字符串结束标志:一次打通编译、main、ASCII、转义字符与注释
c语言·c++