← Home

993. Cousins in Binary Tree

LeetCode article · C++ solution
Website made by wuisabel-gif · Original C++ code by keineahnung2345
two pointersC++Markdown
993

The trick here is to name the state correctly, then let the implementation follow. For 993. Cousins in Binary Tree, the solution in this repository is mainly a two pointers solution.

Guide

What?

We want to turn the problem statement into a smaller set of decisions the computer can repeat safely. Instead of trying to be clever immediately, read the code as a sequence of questions:

  • What state are we keeping?
  • How do we move from one state to the next?
  • When do we know the answer is already determined?

For this file, the main tools are: two pointers.

Guide

When?

This pattern shows up when the brute force version has too many repeated checks, too many possible branches, or too much bookkeeping to do by hand. The accepted code reduces that pressure by storing exactly the information that remains useful later.

The important function names to track are dfs, isCousins.

Guide

Why?

The solution works because it narrows the problem until every update has a clear reason to exist.

  • A map keeps the lookup side cheap; the code pays a little memory to avoid repeated searching.
  • The final return is not magic; it is the invariant after the loops or recursion have finished doing their accounting.

Guide

How?

Walk through the solution in this order:

  1. Read the setup variables first.
  2. Follow the main loop or recursive helper next.
  3. Watch where invalid states get skipped.
  4. Check which value survives to the return statement.

The most important competitive-programming habit here is to trust the invariant. Once the invariant is right, the loops become much less scary.

Guide

Complexity

  • Time: O(N), where N is the number of nodes in the tree.
  • Space: O(N).

Guide

C++ Solution

Your submission

The accepted solution

solution.cpp
01/**
02In a binary tree, the root node is at depth 0, and children of each depth k node are at depth k+1.
03
04Two nodes of a binary tree are cousins if they have the same depth, but have different parents.
05
06We are given the root of a binary tree with unique values, and the values x and y of two different nodes in the tree.
07
08Return true if and only if the nodes corresponding to the values x and y are cousins.
09
10Example 1:
11
12
13Input: root = [1,2,3,4], x = 4, y = 3
14Output: false
15Example 2:
16
17
18Input: root = [1,2,3,null,4,null,5], x = 5, y = 4
19Output: true
20Example 3:
21
22
23
24Input: root = [1,2,3,null,4], x = 2, y = 3
25Output: false
26 
27
28Note:
29
30The number of nodes in the tree will be between 2 and 100.
31Each node has a unique integer value from 1 to 100.
32**/
33
34/**
35Approach 1: Annotate Parent and Depth
36Intuition
37
38Nodes are cousins if they have the same depth but different parents. 
39A straightforward approach is to be able to know the parent and depth of each node.
40
41Algorithm
42
43We can use a depth-first search to annotate each node. 
44For each node with parent par and depth d, we will record results in hashmaps: 
45parent[node.val] = par and depth[node.val] = d.
46**/
47
48/**
49Complexity Analysis
50
51Time Complexity: O(N), where N is the number of nodes in the tree.
52
53Space Complexity: O(N). 
54**/
55
56//Runtime: 12 ms, faster than 23.79% of C++ online submissions for Cousins in Binary Tree.
57//Memory Usage: 15.5 MB, less than 5.08% of C++ online submissions for Cousins in Binary Tree.
58
59/**
60 * Definition for a binary tree node.
61 * struct TreeNode {
62 *     int val;
63 *     TreeNode *left;
64 *     TreeNode *right;
65 *     TreeNode(int x) : val(x), left(NULL), right(NULL) {}
66 * };
67 */
68class Solution {
69public:
70    map<int, int> depth;
71    map<int, TreeNode*> parent;
72    
73    void dfs(TreeNode* node, TreeNode* par){
74        if(node!=NULL){
75            cout << node-> val;
76            depth[node->val] = par!=NULL?1+depth[par->val]:0;
77            //can't use parent.insert(node->val, par)!
78            parent[node->val] = par;
79            dfs(node->left, node);
80            dfs(node->right, node);
81        }
82    }
83    
84    bool isCousins(TreeNode* root, int x, int y) {
85        dfs(root, NULL);
86        return (depth[x] == depth[y] && parent[x] != parent[y]);
87    }
88};

Cost

Complexity

Time
O(N), where N is the number of nodes in the tree.
Dominated by the main traversal, recursion, or data-structure operations in the code.
Space
O(N).
Auxiliary state plus the answer structure where the problem requires one.