55
55
56
56
<!-- 这里可写通用的实现逻辑 -->
57
57
58
- ** 1. BFS 实现 **
58
+ ** 方法一: BFS**
59
59
60
- 可以利用数组 p, d 记录每个节点对应的父节点以及深度 。
60
+ 我们定义一个队列 $q$,队列中存储的是节点和其父节点。初始时,将根节点和空节点放入队列中 。
61
61
62
- ** 2. DFS 实现**
62
+ 每次从队列中取出一个节点,如果该节点的值为 $x$ 或 $y$,则记录该节点的父节点和深度。如果该节点的左右子节点不为空,则将左右子节点和该节点放入队列中。
63
+
64
+ 当队列中所有节点都处理完毕后,如果 $x$ 和 $y$ 的深度相同且父节点不同,则返回 $true$,否则返回 $false$。
65
+
66
+ 时间复杂度 $O(n)$,空间复杂度 $O(n)$。其中 $n$ 是二叉树的节点数。
67
+
68
+ ** 方法二:DFS**
69
+
70
+ 我们设计一个函数 $dfs(root, fa, d)$,表示从根节点 $root$ 出发,其父节点为 $fa$,深度为 $d$,进行深度优先搜索。
71
+
72
+ 在函数中,我们首先判断当前节点是否为空,如果为空,则直接返回。如果当前节点的值为 $x$ 或 $y$,则记录该节点的父节点和深度。然后对当前节点的左右子节点分别调用函数 $dfs$,其中父节点为当前节点,深度为当前深度加 $1$。即 $dfs(root.left, root, d + 1)$ 和 $dfs(root.right, root, d + 1)$。
73
+
74
+ 当整棵二叉树遍历完毕后,如果 $x$ 和 $y$ 的深度相同且父节点不同,则返回 $true$,否则返回 $false$。
75
+
76
+ 时间复杂度 $O(n)$,空间复杂度 $O(n)$。其中 $n$ 是二叉树的节点数。
63
77
64
78
<!-- tabs:start -->
65
79
77
91
# self.left = left
78
92
# self.right = right
79
93
class Solution :
80
- def isCousins (self , root : TreeNode, x : int , y : int ) -> bool :
81
- p = list ( range ( 110 ) )
82
- d = list ( range ( 110 ))
83
- q = deque([root])
84
- i = 0
94
+ def isCousins (self , root : Optional[ TreeNode] , x : int , y : int ) -> bool :
95
+ q = deque([(root, None )] )
96
+ d = 0
97
+ p1 = p2 = None
98
+ d1 = d2 = 0
85
99
while q:
86
- n = len (q)
87
- for _ in range (n):
88
- node = q.popleft()
89
- d[node.val] = i
100
+ for _ in range (len (q)):
101
+ node, fa = q.popleft()
102
+ if node.val == x:
103
+ p1, d1 = fa, d
104
+ if node.val == y:
105
+ p2, d2 = fa, d
90
106
if node.left:
91
- p[node.left.val] = node.val
92
- q.append(node.left)
107
+ q.append((node.left, node))
93
108
if node.right:
94
- q.append(node.right)
95
- p[node.right.val] = node.val
96
- i += 1
97
- return p[x] != p[y] and d[x] == d[y]
109
+ q.append((node.right, node))
110
+ d += 1
111
+ return p1 != p2 and d1 == d2
98
112
```
99
113
100
114
DFS:
@@ -107,22 +121,20 @@ DFS:
107
121
# self.left = left
108
122
# self.right = right
109
123
class Solution :
110
- def isCousins (self , root : TreeNode, x : int , y : int ) -> bool :
111
- p1 = p2 = d1 = d2 = None
112
-
113
- def dfs (root , p , d ):
124
+ def isCousins (self , root : Optional[TreeNode], x : int , y : int ) -> bool :
125
+ def dfs (root , fa , d ):
114
126
if root is None :
115
127
return
116
- nonlocal p1, p2, d1, d2, x, y
117
128
if root.val == x:
118
- p1, d1 = p , d
129
+ t[ 0 ] = (fa , d)
119
130
if root.val == y:
120
- p2, d2 = p , d
131
+ t[ 1 ] = (fa , d)
121
132
dfs(root.left, root, d + 1 )
122
133
dfs(root.right, root, d + 1 )
123
134
135
+ t = [None , None ]
124
136
dfs(root, None , 0 )
125
- return p1 != p2 and d1 == d2
137
+ return t[ 0 ][ 0 ] != t[ 1 ][ 0 ] and t[ 0 ][ 1 ] == t[ 1 ][ 1 ]
126
138
```
127
139
128
140
### ** Java**
@@ -149,28 +161,33 @@ BFS:
149
161
*/
150
162
class Solution {
151
163
public boolean isCousins (TreeNode root , int x , int y ) {
152
- int [] p = new int [ 110 ] ;
153
- int [] d = new int [ 110 ] ;
154
- Deque<TreeNode > q = new ArrayDeque<> ();
155
- q. offer(root);
156
- int i = 0 ;
164
+ TreeNode p1 = null , p2 = null ;
165
+ int d1 = 0 , d2 = 0 ;
166
+ Deque<TreeNode [] > q = new ArrayDeque<> ();
167
+ q. offer(new TreeNode []{ root, null } );
168
+ int d = 0 ;
157
169
while (! q. isEmpty()) {
158
- int n = q. size();
159
- while (n-- > 0 ) {
160
- TreeNode node = q. poll();
161
- d[node. val] = i;
170
+ for (int n = q. size(); n > 0 ; -- n) {
171
+ var p = q. poll();
172
+ TreeNode node = p[0 ], fa = p[1 ];
173
+ if (node. val == x) {
174
+ p1 = fa;
175
+ d1 = d;
176
+ }
177
+ if (node. val == y) {
178
+ p2 = fa;
179
+ d2 = d;
180
+ }
162
181
if (node. left != null ) {
163
- q. offer(node. left);
164
- p[node. left. val] = node. val;
182
+ q. offer(new TreeNode []{node. left, node});
165
183
}
166
184
if (node. right != null ) {
167
- q. offer(node. right);
168
- p[node. right. val] = node. val;
185
+ q. offer(new TreeNode []{node. right, node});
169
186
}
170
187
}
171
- ++ i ;
188
+ ++ d ;
172
189
}
173
- return p[x] != p[y] && d[x] == d[y] ;
190
+ return p1 != p2 && d1 == d2 ;
174
191
}
175
192
}
176
193
```
229
246
230
247
``` cpp
231
248
/* *
232
- * Definition for a binary tree node->
249
+ * Definition for a binary tree node.
233
250
* struct TreeNode {
234
251
* int val;
235
252
* TreeNode *left;
@@ -242,29 +259,34 @@ BFS:
242
259
class Solution {
243
260
public:
244
261
bool isCousins(TreeNode* root, int x, int y) {
245
- vector<int > p(110);
246
- vector<int > d(110);
247
- queue<TreeNode* > q;
248
- q.push(root);
249
- int i = 0;
262
+ TreeNode* p1 = nullptr;
263
+ TreeNode* p2 = nullptr;
264
+ int d1 = 0, d2 = 0;
265
+ queue<pair<TreeNode* , TreeNode* >> q;
266
+ q.emplace(root, nullptr);
267
+ int d = 0;
250
268
while (!q.empty()) {
251
- int n = q.size();
252
- while (n--) {
253
- auto node = q.front();
254
- d[ node->val] = i;
269
+ for (int n = q.size(); n; --n) {
270
+ auto [ node, fa] = q.front();
255
271
q.pop();
272
+ if (node->val == x) {
273
+ p1 = fa;
274
+ d1 = d;
275
+ }
276
+ if (node->val == y) {
277
+ p2 = fa;
278
+ d2 = d;
279
+ }
256
280
if (node->left) {
257
- q.push(node->left);
258
- p[ node->left->val] = node->val;
281
+ q.emplace(node->left, node);
259
282
}
260
283
if (node->right) {
261
- q.push(node->right);
262
- p[ node->right->val] = node->val;
284
+ q.emplace(node->right, node);
263
285
}
264
286
}
265
- ++i ;
287
+ ++d ;
266
288
}
267
- return p [ x ] != p [ y ] && d [ x ] == d [ y ] ;
289
+ return p1 != p2 && d1 == d2 ;
268
290
}
269
291
};
270
292
```
@@ -285,33 +307,27 @@ DFS:
285
307
*/
286
308
class Solution {
287
309
public:
288
- TreeNode* p1;
289
- TreeNode* p2;
290
- int d1, d2;
291
- int x, y;
292
-
293
310
bool isCousins(TreeNode* root, int x, int y) {
294
- this->x = x;
295
- this->y = y;
311
+ TreeNode* p1, *p2;
312
+ int d1, d2;
313
+ function<void(TreeNode*, TreeNode*, int)> dfs = [&](TreeNode* root, TreeNode* fa, int d) {
314
+ if (!root) {
315
+ return;
316
+ }
317
+ if (root->val == x) {
318
+ p1 = fa;
319
+ d1 = d;
320
+ }
321
+ if (root->val == y) {
322
+ p2 = fa;
323
+ d2 = d;
324
+ }
325
+ dfs(root->left, root, d + 1);
326
+ dfs(root->right, root, d + 1);
327
+ };
296
328
dfs(root, nullptr, 0);
297
329
return p1 != p2 && d1 == d2;
298
330
}
299
-
300
- void dfs(TreeNode* root, TreeNode* p, int d) {
301
- if (!root) return;
302
- if (root->val == x)
303
- {
304
- p1 = p;
305
- d1 = d;
306
- }
307
- if (root->val == y)
308
- {
309
- p2 = p;
310
- d2 = d;
311
- }
312
- dfs(root->left, root, d + 1);
313
- dfs(root->right, root, d + 1);
314
- }
315
331
};
316
332
```
317
333
@@ -329,30 +345,31 @@ BFS:
329
345
* }
330
346
*/
331
347
func isCousins (root *TreeNode , x int , y int ) bool {
332
- p := make ([]int , 110 )
333
- d := make ([]int , 110 )
334
- var q []*TreeNode
335
- q = append (q, root)
336
- i := 0
348
+ type pair struct { node, fa *TreeNode }
349
+ q := []pair{pair{root, nil }}
350
+ var p1 , p2 *TreeNode
351
+ var d , d1 , d2 int
337
352
for len (q) > 0 {
338
- n := len (q)
339
- for n > 0 {
340
- node := q[0 ]
353
+ for n := len (q); n > 0 ; n-- {
354
+ p := q[0 ]
341
355
q = q[1 :]
342
- n--
343
- d[node.Val ] = i
356
+ node , fa := p.node , p.fa
357
+ if node.Val == x {
358
+ p1, d1 = fa, d
359
+ }
360
+ if node.Val == y {
361
+ p2, d2 = fa, d
362
+ }
344
363
if node.Left != nil {
345
- q = append (q, node.Left )
346
- p[node.Left .Val ] = node.Val
364
+ q = append (q, pair{node.Left , node})
347
365
}
348
366
if node.Right != nil {
349
- q = append (q, node.Right )
350
- p[node.Right .Val ] = node.Val
367
+ q = append (q, pair{node.Right , node})
351
368
}
352
369
}
353
- i ++
370
+ d ++
354
371
}
355
- return p[x] != p[y] && d[x] == d[y]
372
+ return p1 != p2 && d1 == d2
356
373
}
357
374
```
358
375
@@ -367,30 +384,25 @@ DFS:
367
384
* Right *TreeNode
368
385
* }
369
386
*/
370
- var p1 *TreeNode
371
- var p2 *TreeNode
372
- var d1 int
373
- var d2 int
374
-
375
387
func isCousins (root *TreeNode , x int , y int ) bool {
376
- dfs (root, nil , x, y, 0 )
377
- return p1 != p2 && d1 == d2
378
- }
379
-
380
- func dfs ( root , p * TreeNode , x , y , d int ) {
381
- if root == nil {
382
- return
383
- }
384
- if root. Val == x {
385
- p1 = p
386
- d1 = d
387
- }
388
- if root. Val == y {
389
- p2 = p
390
- d2 = d
388
+ var p1 , p2 *TreeNode
389
+ var d1 , d2 int
390
+ var dfs func (*TreeNode, *TreeNode, int )
391
+ dfs = func (root *TreeNode, fa *TreeNode, d int ) {
392
+ if root == nil {
393
+ return
394
+ }
395
+ if root. Val == x {
396
+ p1, d1 = fa, d
397
+ }
398
+ if root. Val == y {
399
+ p2, d2 = fa, d
400
+ }
401
+ dfs (root. Left , root, d+ 1 )
402
+ dfs (root. Right , root, d+ 1 )
391
403
}
392
- dfs (root. Left , root, x, y, d+ 1 )
393
- dfs (root. Right , root, x, y, d+ 1 )
404
+ dfs (root, nil , 0 )
405
+ return p1 != p2 && d1 == d2
394
406
}
395
407
```
396
408
0 commit comments