题目:
给你一棵二叉树的根节点 root ,翻转这棵二叉树,并返回其根节点。
思路:
遍历到每一个节点,遍历到的时候就交换其左右孩子。
遍历方式我这写了四种所以就有四种方法。
代码:
介绍四种方法:
①:递归法
思路:
首先递归三部曲:
1:确定递归函数的参数和返回值
TreeNode* invertTree(TreeNode* root)
2:确定终止条件
if (root == NULL) return root;
3:确定单层递归的逻辑
swap(root->left, root->right);
invertTree(root->left);
invertTree(root->right);
先翻转根的左节点、根的右节点,然后反转根的左子树,根的右子树。
class Solution {
public:
TreeNode* invertTree(TreeNode* root) {
if (root == NULL) return root;
swap(root->left, root->right); // 中
invertTree(root->left); // 左
invertTree(root->right); // 右
return root;
}
};
②:前面介绍前中后序迭代代码写法,这个类似,多了一个:swap(node->left, node->right);
。这个是前序写法,这个是首先处理根的左右孩子,然后处理左孩子的左右,然后处理左孩子的左孩子的左右,然后直到结束,然后回退。这个方法会遍历到每一个节点,那么会转换所有的左右孩子。每个节点的先后转换顺序并不会影响结果,只要转换了,最后结果都一样。
class Solution {
public:
TreeNode* invertTree(TreeNode* root) {
if (root == NULL) return root;
stack<TreeNode*> st;
st.push(root);
while(!st.empty()) {
TreeNode* node = st.top(); // 中
st.pop();
swap(node->left, node->right);
if(node->right) st.push(node->right); // 右
if(node->left) st.push(node->left); // 左
}
return root;
}
};
③:类似于前中后序的统一写法多了一个:swap(node->left, node->right);
。这个也是前序遍历会遍历到每一个节点 else内的 node 即根 node。当node == NULL的时候即下一个节点是中点,那么交换他的左右孩子即可。这样依旧是会遍历到每一个节点。交换每一个节点的左右孩子。
class Solution {
public:
TreeNode* invertTree(TreeNode* root) {
stack<TreeNode*> st;
if (root != NULL) st.push(root);
while (!st.empty()) {
TreeNode* node = st.top();
if (node != NULL) {
st.pop();
if (node->right) st.push(node->right); // 右
if (node->left) st.push(node->left); // 左
st.push(node); // 中
st.push(NULL);
} else {
st.pop();
node = st.top();
st.pop();
swap(node->left, node->right); // 节点处理逻辑
}
}
return root;
}
};
④:层序遍历方法
一行一行的去除每个节点,去除时会交换。
class Solution {
public:
TreeNode* invertTree(TreeNode* root) {
queue<TreeNode*> que;
if (root != NULL) que.push(root);
while (!que.empty()) {
int size = que.size();
for (int i = 0; i < size; i++) {
TreeNode* node = que.front();
que.pop();
swap(node->left, node->right); // 节点处理
if (node->left) que.push(node->left);
if (node->right) que.push(node->right);
}
}
return root;
}
};