【问题】给定一个二叉树,检查它是否是镜像对称的。
例如,二叉树 [1,2,2,3,4,4,3] 是对称的。 1 / \ 2 2 / \ / \ 3 4 4 3 但是下面这个 [1,2,2,null,3,null,3] 则不是镜像对称的: 1 / \ 2 2 \ \ 3 3
【思路】对称二叉树,很明显我们需要使用层次遍历,同样的,我们使用递归和非递归两种方法来解决这个问题,通常递归的方法都要简单一些,但是在大的工程项目中一般不使用递归(出错不容易分析)。层次遍历我们使用队列结构!注意递归版本的递归退出条件,如果两者都为空,则说明到达了叶节点,返回true. 如果只有一个为空,直接返回false, 因为这种条件下无法比较!
/** * Definition for a binary tree node. * struct TreeNode { * int val; * TreeNode *left; * TreeNode *right; * TreeNode(int x) : val(x), left(NULL), right(NULL) {} * }; */ class Solution { public: bool dfs(TreeNode* l, TreeNode* r){ if(l == nullptr && r == nullptr){ return true; } if(l == nullptr || r == nullptr){ return false; } if (l->val == r->val){ return dfs(l->left, r->right) && dfs(l->right, r->left); } return false; } bool isSymmetric(TreeNode* root) { return dfs(root, root); } };
当然层次遍历也是有非递归版本的,我们可以使用一个size遍历来一次处理一层数据,由于一层数据是相对于中心对称的,因此我们可以分别使用一个堆和一个栈结构来处理!当然了使用数组也没有问题的啦!
/** * Definition for a binary tree node. * struct TreeNode { * int val; * TreeNode *left; * TreeNode *right; * TreeNode(int x) : val(x), left(NULL), right(NULL) {} * }; */ class Solution { public: bool isSymmetric(TreeNode* root) { if(root == nullptr) return true; queue<TreeNode*> que; queue<int> q; stack<int> p; que.push(root); while(!que.empty()){ int size = que.size(); while(size--){ TreeNode* tmp = que.front(); que.pop(); if(tmp->left != nullptr){ q.push(tmp->left->val); p.push(tmp->left->val); que.push(tmp->left); }else{ q.push(-1); // 后面判断时使用 p.push(-1); } if(tmp->right != nullptr){ q.push(tmp->right->val); p.push(tmp->right->val); que.push(tmp->right); }else{ q.push(-1); p.push(-1); } } while(!p.empty()){ if(p.top() == q.front()){ p.pop(); q.pop(); }else{ return false; } } } return true; } };