vault backup: 2022-07-17 11:13:12

This commit is contained in:
juan 2022-07-17 11:13:12 +08:00
parent ec7733cae6
commit b66312368e
4 changed files with 113 additions and 39 deletions

View file

@ -64,6 +64,13 @@ Initially, all next pointers are set to `NULL`.
> [!summary]
> This is a #BFS problem, and cam be optimized
> It relies on the fact that it is perfect binary tree.
> The core part for optimization is utilizing ptr->next
Using ptr->next in DFS and iteration enable us to traverse
between branches like in BFS
![[DFS with links.png]]
##### BFS way of doing this, O(n)time, O(n + 1)space
@ -71,19 +78,33 @@ simple BFS, for each level, connect the node to the next.
Remember to get the for loop right.
##### BFS-like iteration, two pointers
##### BFS-like iteration, two pointers, O(n)time, O(n + 1)space
We utilize the ->next property to link ptr->left->right->next to ptr->right->left
We utilize the ->next property to link
ptr->left->right->next to ptr->right->left
![[Leetcode Populating next right ptr-2.png]]
##### Also can be done with DFS
We can't use ptr->left->right->next = ptr->right->left,
since this is only one level, and doesn't work on two levels:
![[Leetcode Populating next right ptr-1.png]]
##### Also can be done with DFS O(n), O(n)
We recursively fill next pointers the level below current.
Base case:
- Root->left is empty, which means this is the leaf level, quit.
Pseudo-code:
1. Check for base case
1. link root->left and root->right
1. link root->right and root->next->left (if root->next is valid.)
### Solution
BFS unoptimized:
DFS:
```cpp
/*
// Definition for a Node.
@ -104,40 +125,93 @@ public:
*/
class Solution {
public:
Node* connect(Node* root) {
// BFS.
// Can we do it with DFS?
queue<Node*> todo;
if (root && root->left && root->right) {
todo.push(root->left);
todo.push(root->right);
}
Node *ptr, *nextPtr;
while (!todo.empty()) {
nextPtr = todo.front();
todo.pop();
for (size_t i = 0, size = todo.size(); i < size; i++) {
ptr = nextPtr;
nextPtr = todo.front();
todo.pop();
ptr->next = nextPtr;
if (ptr->left) {
todo.push(ptr->left);
todo.push(ptr->right);
}
}
if (nextPtr->left) {
todo.push(nextPtr->left);
todo.push(nextPtr->right);
}
}
return root;
void conn(Node *root) {
// preorder DFS, here we go!
// It assumes at least one level, which doesn't include []
if (root->left) {
root->left->next = root->right;
if (root->next) {
root->right->next = root->next->left;
}
conn(root->left);
conn(root->right);
}
}
public:
Node *connect(Node *root) {
if (root) {
conn(root);
}
return root;
}
};
```
Iterative, O(n)time O(1)space
```cpp
class Solution {
public:
Node *connect(Node *root) {
// iteration
Node *ptr = root;
Node *nextPtr = nullptr;
while (ptr && ptr->left) {
ptr->left->next = ptr->right;
if (!nextPtr) {
nextPtr = ptr->left;
}
if (!ptr->next) {
ptr = nextPtr;
nextPtr = nullptr;
} else {
ptr->right->next = ptr->next->left;
ptr = ptr->next;
}
}
return root;
}
};
```
BFS unoptimized:
```cpp
class Solution {
public:
Node *connect(Node *root) {
// BFS.
// Can we do it with DFS?
queue<Node *> todo;
if (root && root->left && root->right) {
todo.push(root->left);
todo.push(root->right);
}
Node *ptr, *nextPtr;
while (!todo.empty()) {
nextPtr = todo.front();
todo.pop();
for (size_t i = 0, size = todo.size(); i < size; i++) {
ptr = nextPtr;
nextPtr = todo.front();
todo.pop();
ptr->next = nextPtr;
if (ptr->left) {
todo.push(ptr->left);
todo.push(ptr->right);
}
}
if (nextPtr->left) {
todo.push(nextPtr->left);
todo.push(nextPtr->right);
}
}
return root;
}
};
```

BIN
_files/DFS with links.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 66 KiB

View file

Before

Width:  |  Height:  |  Size: 35 KiB

After

Width:  |  Height:  |  Size: 35 KiB

View file

Before

Width:  |  Height:  |  Size: 20 KiB

After

Width:  |  Height:  |  Size: 20 KiB