判断是否有路径
bool hasPathSum(TreeNode *root, int sum) {
if(root==NULL)
return false;
sum-=root->val;
if(root->left==NULL&&root->right==NULL&&sum==0)
return true;
return hasPathSum(root->left,sum)||hasPathSum(root->right,sum);
}
思路1 遍历二叉树,记录所有叶子结点,然后依次向上遍历到根节点。路径和等于给定值,就说明符合;
vector<vector<int> > pathSum(TreeNode *root, int sum) {
vector<vector<int>> result;
if(root==NULL)
return result;
unordered_map<TreeNode*,TreeNode*> mp; //存放父子节点的关系
vector<TreeNode*> leaf; //存放子节点
queue<TreeNode*> que; //按层遍历
que.push(root);
mp[root]=root;
while(!que.empty()){
TreeNode* p=que.front();
que.pop();
if(p->left){
mp[p->left]=p;
que.push(p->left);
}
if(p->right){
mp[p->right]=p;
que.push(p->right);
}
if(p->left==NULL&&p->right==NULL)
leaf.push_back(p);
}
for(TreeNode* q:leaf){
vector<int> path;
int count=0;
while(q!=root){
count+=q->val;
path.push_back(q->val);
q=mp[q];
}
count+=q->val;
path.push_back(q->val);
if(count==sum){
//reverse(path.begin(),path.end());
result.push_back(path);
}
}
return result;
}
思路 2: 递归
从根节点开始往下遍历,用给定值减去当前节点值,如果当前节点是叶子结点,切减去后值为0,就说明找到一条路径。否则,递归左右子树
vector<vector<int> > pathSum(TreeNode *root, int sum) {
vector<vector<int>> result;
if(root==NULL)
return result;
vector<int> path;
pathSumCore(root,sum,path,result);
return result;
}
void pathSumCore(TreeNode* root,int sum,vector<int> path,vector<vector<int>>& result){ //path 的参数不能是引用,因为每次都要复制
if(root==NULL)
return;
path.push_back(root->val);
sum-=root->val; //减去当前结点的值
if(root->left==NULL&&root->right==NULL&&sum==0)
result.push_back(path);
pathSumCore(root->left,sum,path,result);
pathSumCore(root->right,sum,path,result);
}
path参数也可以递归。只用每次做完后把当前节点在弹出去,
vector<vector<int> > pathSum(TreeNode *root, int sum) {
vector<vector<int>> result;
if(root==NULL)
return result;
vector<int> path;
pathSumCore(root,sum,path,result);
return result;
}
void pathSumCore(TreeNode* root,int sum,vector<int>& path,vector<vector<int>>& result){
if(root==NULL)
return;
path.push_back(root->val);
sum-=root->val;
if(root->left==NULL&&root->right==NULL&&sum==0)
result.push_back(path);
pathSumCore(root->left,sum,path,result);
pathSumCore(root->right,sum,path,result);
path.pop_back(); //引用 做完后要弹出当前元素
}