力扣刷题记录-二叉树展开为链表
力扣刷题记录-二叉树展开为链表
题目描述
给定一个二叉树,原地将它展开为一个单链表。展开后的单链表应该同样使用 TreeNode
,其中 right
子指针指向链表中下一个结点,而 left
子指针始终为 null
。
解题思路
要将二叉树展开为链表,可以采用前序遍历的方式,将每个节点的左子树插入到右子树的位置,同时将原来的右子树接到左子树的最右节点。
具体步骤如下:
- 前序遍历:遍历二叉树的每个节点。
- 展开操作:
- 如果当前节点的左子树不为空,找到左子树的最右节点。
- 将当前节点的右子树接到左子树的最右节点。
- 将当前节点的左子树移动到右子树的位置,并将左子树置为
null
。
- 递归处理:对每个节点重复上述操作,直到所有节点处理完毕。
代码实现
以下是 C++ 的实现代码:
#include <iostream>
struct TreeNode {
int val;
TreeNode *left;
TreeNode *right;
TreeNode(int x) : val(x), left(nullptr), right(nullptr) {}
};
class Solution {
public:
void flatten(TreeNode* root) {
if (!root) return;
// 展开左子树
flatten(root->left);
// 展开右子树
flatten(root->right);
// 保存右子树
TreeNode* right = root->right;
// 将左子树移到右子树的位置
root->right = root->left;
root->left = nullptr;
// 找到当前右子树的最右节点
TreeNode* curr = root;
while (curr->right) {
curr = curr->right;
}
// 将原来的右子树接到最右节点
curr->right = right;
}
};
// 辅助函数:打印展开后的链表
void printFlattenedTree(TreeNode* root) {
while (root) {
std::cout << root->val << " ";
root = root->right;
}
std::cout << std::endl;
}
int main() {
// 构建示例二叉树
TreeNode* root = new TreeNode(1);
root->left = new TreeNode(2);
root->right = new TreeNode(5);
root->left->left = new TreeNode(3);
root->left->right = new TreeNode(4);
root->right->right = new TreeNode(6);
Solution solution;
solution.flatten(root);
// 打印展开后的链表
printFlattenedTree(root);
return 0;
}