LeetCode 面试经典 150_二叉树_路径总和(75_112_C++_简单)(DFS)
LeetCode 面试经典 150_二叉树_路径总和(75_112_C++_简单)
- 题目描述:
- 输入输出样例:
- 题解:
- 解题思路:
- 思路一(DFS):
- 代码实现
- 代码实现(思路一(DFS)):
- 以思路一为例进行调试
题目描述:
给你二叉树的根节点 root 和一个表示目标和的整数 targetSum 。判断该树中是否存在 根节点到叶子节点 的路径,这条路径上所有节点值相加等于目标和 targetSum 。如果存在,返回 true ;否则,返回 false 。
叶子节点 是指没有子节点的节点。
输入输出样例:
示例 1:

输入:root = [5,4,8,11,null,13,4,7,2,null,null,null,1], targetSum = 22
输出:true
解释:等于目标和的根节点到叶节点路径如上图所示。
示例 2:

输入:root = [1,2,3], targetSum = 5
输出:false
解释:树中存在两条根节点到叶子节点的路径:
(1 --> 2): 和为 3
(1 --> 3): 和为 4
不存在 sum = 5 的根节点到叶子节点的路径。
示例 3:
输入:root = [], targetSum = 0
输出:false
解释:由于树是空的,所以不存在根节点到叶子节点的路径。
提示:
树中节点的数目在范围 [0, 5000] 内
-1000 <= Node.val <= 1000
-1000 <= targetSum <= 1000
题解:
解题思路:
思路一(DFS):
1、问题的本质是检查是否存在一条从根节点到叶子节点的路径,其路径上所有节点的值之和等于 targetSum。通过递归的方式,遍历树的每一条路径,逐步减去节点的值,直到到达叶子节点。
- 判断当前节点是否为空
- 检查是否到达叶子节点
- 递归遍历左右子树
2、复杂度分析:
① 时间复杂度:O(N),其中 N 是树的节点数。对每个节点访问一次。
② 空间复杂度:O(H),其中 H 是树的高度。空间复杂度主要取决于递归时栈空间的开销,最坏情况下,树呈现链状,空间复杂度为 O(N)。
代码实现
代码实现(思路一(DFS)):
class Solution {
public:// 判断二叉树是否存在一条从根到叶节点的路径,使得路径上的节点值之和等于 targetSumbool hasPathSum(TreeNode* root, int targetSum) {// 如果当前节点为空,返回 false,因为没有路径if(root == nullptr){return false;}// 如果当前节点是叶子节点且剩余的目标和为 0,返回 true// 叶子节点的判断:即左右子树都为空if(targetSum - root->val == 0 && root->left == nullptr && root->right == nullptr){return true;}// 否则,递归判断左子树和右子树是否有满足条件的路径// 继续减少目标和,分别检查左子树和右子树return hasPathSum(root->left, targetSum - root->val) || hasPathSum(root->right, targetSum - root->val);}
};
以思路一为例进行调试
#include<iostream>
#include<vector>
#include<queue>
using namespace std;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(0),left(left),right(right){}
};//层次遍历构建二叉树(-1代表nullptr结点)
TreeNode *createTree(vector<int> nums){if (nums.empty()){return nullptr;}TreeNode *root=new TreeNode(nums[0]);queue<TreeNode *> Q;Q.push(root);int i=1;while (i<nums.size()){TreeNode *curNode=Q.front();Q.pop();if (i<nums.size()&&nums[i]!=-1){curNode->left=new TreeNode(nums[i]);Q.push(curNode->left);}i++;if (i<nums.size()&&nums[i]!=-1){curNode->right=new TreeNode(nums[i]);Q.push(curNode->right);}i++; }return root;
}void inorder(TreeNode *root){if (!root){return;}inorder(root->left);cout<<root->val<<" ";inorder(root->right);
}/** 方法一:深度优先遍历* */
class Solution {
public:// 判断二叉树是否存在一条从根到叶节点的路径,使得路径上的节点值之和等于 targetSumbool hasPathSum(TreeNode* root, int targetSum) {// 如果当前节点为空,返回 false,因为没有路径if(root == nullptr){return false;}// 如果当前节点是叶子节点且剩余的目标和为 0,返回 true// 叶子节点的判断:即左右子树都为空if(targetSum - root->val == 0 && root->left == nullptr && root->right == nullptr){return true;}// 否则,递归判断左子树和右子树是否有满足条件的路径// 继续减少目标和,分别检查左子树和右子树return hasPathSum(root->left, targetSum - root->val) || hasPathSum(root->right, targetSum - root->val);}
};int main(int argc, char const *argv[])
{vector<int> nums={5,4,8,11,-1,13,4,7,2,-1,-1,-1,1};TreeNode* root=createTree(nums);//中序遍历输出二叉树,验证二叉树是否创建正确// inorder(root);return 0;
}
LeetCode 面试经典 150_二叉树_路径总和(75_112)原题链接
欢迎大家和我沟通交流(✿◠‿◠)
