1. 程式人生 > 其它 >【LeetCode】C++ :簡單題 - 樹 235. 二叉搜尋樹的最近公共祖先

【LeetCode】C++ :簡單題 - 樹 235. 二叉搜尋樹的最近公共祖先

技術標籤:LeetCodeleetcode演算法二叉樹

235. 二叉搜尋樹的最近公共祖先

難度簡單511

給定一個二叉搜尋樹, 找到該樹中兩個指定節點的最近公共祖先。

百度百科中最近公共祖先的定義為:“對於有根樹 T 的兩個結點 p、q,最近公共祖先表示為一個結點 x,滿足 x 是 p、q 的祖先且 x 的深度儘可能大(一個節點也可以是它自己的祖先)。”

例如,給定如下二叉搜尋樹: root =[6,2,8,0,4,7,9,null,null,3,5]

示例 1:

輸入: root = [6,2,8,0,4,7,9,null,null,3,5], p = 2, q = 8
輸出: 6 
解釋: 
節點 2 和節點 8 的最近公共祖先是 6。

示例 2:

輸入: root = [6,2,8,0,4,7,9,null,null,3,5], p = 2, q = 4
輸出: 2
解釋: 節點 2 和節點 4 的最近公共祖先是 2, 因為根據定義最近公共祖先節點可以為節點本身。

說明:

  • 所有節點的值都是唯一的。
  • p、q 為不同節點且均存在於給定的二叉搜尋樹中。

這題的解題思路很好,我從解題中看到從各節點路徑中找公共祖先時,程式碼思路就一下子展開了。

只不過在getPath函式裡面差點想用遞迴寫了,遞迴啊樹啊,深植我心。

/**
 * Definition for a binary tree node.
 * struct TreeNode {
 *     int val;
 *     TreeNode *left;
 *     TreeNode *right;
 *     TreeNode(int x) : val(x), left(NULL), right(NULL) {}
 * };
 */

class Solution {
public:
    TreeNode* lowestCommonAncestor(TreeNode* root, TreeNode* p, TreeNode* q) {
        vector<TreeNode*> path_p = getPath(root, p);
        vector<TreeNode*> path_q = getPath(root, q);
        
        TreeNode* res;
        // for(int i = path_p.size()-1, j = path_q.size()-1; i > -1, j > -1; i--, j--){
        //     if(path_p[i] == path_q[j]){
        //         res = path_q[i];
        //     }
        // }
        for (int i = 0; i < path_p.size() && i <path_q.size(); i++){
            if(path_p[i] == path_q[i]){
                res = path_q[i];
            }else{
                break;
            }
        }
        return res;

    }
    vector<TreeNode*> getPath(TreeNode* root, TreeNode* target){
        vector<TreeNode*> path;
        TreeNode* node = root;
        while(node != target){
            path.push_back(node);
            if(node->val < target->val){
                node = node->right;
            }else{
                node = node->left;
            }
        }
        path.push_back(node);
        return path;
    }
};

程式碼中註釋部分是不對的,在這裡記錄一下錯誤的原因,以便以後做題時能夠認識這種錯誤避免這樣的誤區。

當得到到達兩個節點的路徑時,路徑的長度是不一定相等, 雖然知道路徑的最後一個節點是所要到達的節點,但在這之前的路徑節點很多是未知的,因此不能貿然的將path陣列倒著去遵照最近的公共祖先,原因是:路徑長度不一樣,那樣迴圈很有可能一個路徑陣列提前結束了而結束迴圈,最終找不到答案。

總結一點:

對於找公共元素時,往往不能取巧,還是按照規矩來比較好。