目录
题目描述:
思考:考虑对称,很明显,我们需要两个指针,对称指向相应位置,如果不对称或者数值不对,返回false!
下面介绍两种解法:递归解法和迭代解法:
递归
递归三部曲:
1)返回条件
2)递归条件
3)返回值
本题已经确定了返回值,我们首先要确定root是否为空,但是这如果直接写在递归函数里很明显是不划算的,所以我们单独写一个函数判断初始root是否为null.
那么递归条件怎么想呢?
我们考虑以下情况:
①.left,right都不为空
②.其中一个为空
③.都不为空且值相等
④.都不为空但是只值不相等
只有第四种情况是可以进一步递归的,我们就递归进入下一步check(left->left,right->right),check(left->right,right->left),两者只有都为true的时候结果才是true,我们直接返回即可!
递归代码
class Solution {
public:
bool check(TreeNode* left, TreeNode* right)
{
if (!left && !right) return true;
if ((!left && right) || (!right && left)) return false;
if (left->val == right->val) return check(left->left, right->right) && check(left->right, right->left);
else return false;
}
bool isSymmetric(TreeNode* root) {
if (!root) return true;
return check(root->left, root->right);
}
};
迭代
我们还记得前序遍历的顺序是根左右,根据对称性,左==右, 那么根右左也是和根左右一样的结果,我们可以利用这一点来解题.利用两个栈来存储,判断是否对称.
正常栈:先压入右子树,再压入左子树
反常栈:先压入左子树,再压入右子树
根据最后两者出栈的值,判断.
迭代代码
bool isSymmetric(TreeNode* root) {
if (!root) return true;
stack<TreeNode*> nor;
TreeNode* f;
TreeNode* s;
stack<TreeNode*> rev;
nor.push(root);
rev.push(root);
while (!nor.empty() && !rev.empty())
{
f = nor.top();
nor.pop();
s = rev.top();
rev.pop();
if (!f && !s) continue;
if((!f&&s)||(f&&!s)) return false;
if (f->val != s->val) return false;
nor.push(f->right);
nor.push(f->left);
rev.push(s->left);
rev.push(s->right);
}
return true;
}