114. Flatten Binary Tree to Linked List
仅供自己学习
思路:
题目要求最终的链表是按先序遍历的顺序排序,但如果用先序遍历,会导致右孩子丢失,所以后序的方法,自底向上来移动,那么下意识会想到对左子树DFS直到没有左子树。再将该节点的左子树放到该节点右子树位置,再将原右子树放到新右子树的右子树位置即可。
代码
1 /** 2 * Definition for a binary tree node. 3 * struct TreeNode { 4 * int val; 5 * TreeNode *left; 6 * TreeNode *right; 7 * TreeNode() : val(0), left(nullptr), right(nullptr) {} 8 * TreeNode(int x) : val(x), left(nullptr), right(nullptr) {} 9 * TreeNode(int x, TreeNode *left, TreeNode *right) : val(x), left(left), right(right) {} 10 * }; 11 */ 12 class Solution { 13 public: 14 void flatten(TreeNode* root) { 15 if(root==NULL ||!root->left&&!root->right) return ; //因为此方法会对叶子节点进行,但没必要,所以加此条件去除操作叶子节点 16 if(root->left)flatten(root->left); 17 if(root->right)flatten(root->right); 18 TreeNode* temp = root->right; 19 root->right=root->left; 20 root->left=NULL; 21 while(root->right) root=root->right; //当新右子树很多结点时就需要循环到最后的一个右子树,再连接上去 22 root->right= temp; 23 24 } 25 };
上面的方法是使用的递归,还可非递归的方法。发现如果是非递归的方法就需要多使用两个以上的指针来辅助操作,一个静止用于定位最初的结点,另一个用于移动操作结点。
第二种方法是将root的右子树连接到左子树中的最右的叶子节点后面,再将左子树连到root右子树的位置,将左子树设为NULL即可。和上面不同的是这个方法是自顶向下的操作。
代码:
/** * Definition for a binary tree node. * struct TreeNode { * int val; * TreeNode *left; * TreeNode *right; * TreeNode() : val(0), left(nullptr), right(nullptr) {} * TreeNode(int x) : val(x), left(nullptr), right(nullptr) {} * TreeNode(int x, TreeNode *left, TreeNode *right) : val(x), left(left), right(right) {} * }; */ class Solution { public: void flatten(TreeNode* root) { TreeNode* cur=root; //用cur指针定位root结点 while(cur){ if(cur->left){ TreeNode* temp=cur->left; while(temp->right) temp=temp->right; //temp指针来操作root右子树连接到左子树最右的叶子节点后 temp->right=cur->right; cur->right=cur->left; cur->left=NULL; } cur=cur->right; } } };
第一种方法使用的后序排序,因为先序排序会丢失右孩子,当遍历到2时,将2连接到1的右子树,那么就会丢失1的右孩子,那如果我们使用一个数据结构存储右孩子呢。这里用stack来存储每个结点的左右子树。
代码:
1 /** 2 * Definition for a binary tree node. 3 * struct TreeNode { 4 * int val; 5 * TreeNode *left; 6 * TreeNode *right; 7 * TreeNode() : val(0), left(nullptr), right(nullptr) {} 8 * TreeNode(int x) : val(x), left(nullptr), right(nullptr) {} 9 * TreeNode(int x, TreeNode *left, TreeNode *right) : val(x), left(left), right(right) {} 10 * }; 11 */ 12 class Solution { 13 public: 14 void flatten(TreeNode* root) { 15 if(root==NULL){ 16 return; 17 } 18 stack<TreeNode*> s; 19 TreeNode* cur = NULL; 20 s.push(root); 21 while(!s.empty()){ 22 TreeNode* temp = s.top(); //返回顶部元素 23 s.pop(); //删除顶部元素 24 if(cur!=NULL){ 25 cur->right = temp; 26 cur->left =NULL; 27 } 28 if(temp->right) s.push(temp->right); //因为是stack先进后出,所以先放入右子树 29 if(temp->left) s.push(temp->left); //左右子树都进入 30 31 32 cur =temp; 33 } 34 35 } 36 };

浙公网安备 33010602011771号