给定一个二叉树,检查它是否是镜像对称的。

例如,二叉树 [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

说明:

如果你可以运用递归和迭代两种方法解决这个问题,会很加分。


考察

1.树的前序遍历

2.如果树的对称前序遍历和树的前序遍历序列一样的,就是对称的二叉树

递归 

  • 时间复杂度:O(n)。因为我们遍历整个输入树一次,所以总的运行时间为 O(n),其中 n是树中结点的总数。
  • 空间复杂度:递归调用的次数受树的高度限制。在最糟糕的情况下,树是线性的,其高度为 O(n)。因此,在最糟糕的情况下,由栈上的递归调用造成的空间复杂度为 O(n)。
/**
* 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) {
//root为空返回真。root不为空开始递归遍历。
return root?isSymmetric(root->left, root->right):true; } bool isSymmetric(TreeNode* r1,TreeNode* r2) { //结束条件1
if(!r1&&!r2)
return true; //结束条件2
if(!r1||!r2)
return false; //返回三方合并
return r1->val==r2->val&&isSymmetric(r1->left,r2->right)&&isSymmetric(r1->right,r2->left);
} };

迭代

除了递归的方法外,我们也可以利用队列进行迭代。队列中每两个连续的结点应该是相等的,而且它们的子树互为镜像。最初,队列中包含的是 root 以及 root。该算法的工作原理类似于 BFS,但存在一些关键差异。每次提取两个结点并比较它们的值。然后,将两个结点的左右子结点按相反的顺序插入队列中。当队列为空时,或者我们检测到树不对称(即从队列中取出两个不相等的连续结点)时,该算法结束。

  • 时间复杂度:O(n)。因为我们遍历整个输入树一次,所以总的运行时间为 O(n),其中 n是树中结点的总数。
  • 空间复杂度:搜索队列需要额外的空间。在最糟糕的情况下,我们不得不向队列中插入O(n) 个结点。因此,空间复杂度为 O(n)。
public boolean isSymmetric(TreeNode root) {
Queue<TreeNode> q = new LinkedList<>();
q.add(root);
q.add(root);
while (!q.isEmpty()) {
TreeNode t1 = q.poll();
TreeNode t2 = q.poll();
if (t1 == null && t2 == null) continue;
if (t1 == null || t2 == null) return false;
if (t1.val != t2.val) return false;
q.add(t1.left);
q.add(t2.right);
q.add(t1.right);
q.add(t2.left);
}
return true;
}

newcoder

/*
struct TreeNode {
int val;
struct TreeNode *left;
struct TreeNode *right;
TreeNode(int x) :
val(x), left(NULL), right(NULL) {
}
};
*/
class Solution {
public:
bool isSymmetrical(TreeNode* pRoot)
{ return Symmetrical(pRoot,pRoot); } bool Symmetrical(TreeNode* pRoot1,TreeNode* pRoot2)
{
if(!pRoot1&&!pRoot2)
return true;
if(!pRoot1||!pRoot2)
return false; if(pRoot1->val!=pRoot2->val)
return false; return Symmetrical(pRoot1->left,pRoot2->right)&&Symmetrical(pRoot1->right,pRoot2->left); } };

最新文章

  1. kindEditor完整认识 PHP上调用并上传图片说明/////////////////////////////z
  2. JSP网站开发基础总结《一》
  3. .assetbundle 和.unity3d 好处
  4. 利用Hive实现求两条相邻数据时间差
  5. hibernate学习(5)——对象状态与一级缓存
  6. Android 环境常见问题
  7. Python动态生成变量
  8. dapper 操作类封装
  9. Speed Limit 分类: POJ 2015-06-09 17:47 9人阅读 评论(0) 收藏
  10. method chaining
  11. Linux 安装挂载时注意事项
  12. hdu 4259 Double Dealing
  13. 基于DOM的XSS注入漏洞简单解析
  14. dede导航设置成单页面内容
  15. SuperSocket源码解析之开篇
  16. Effective Java 第三版——12. 始终重写 toString 方法
  17. discuz 更换域名 导致qq登录不能用的问题
  18. 微信小程序—文件系统
  19. CF115B Lawnmower(贪心)
  20. iOS性能优化技巧

热门文章

  1. (二)异步解决方案之callback
  2. Python 简单的方法爬取b站dnf视频封面
  3. Linux--2 Linux之文档与目录结构、shell基本命令
  4. Excel2010如何实现隔行设置背景色
  5. 模拟虚拟的文件系统initrd/initramfs
  6. Hive:JDBC示例
  7. asp.net web 开发中配置web.config
  8. js和JQuery中offset等属性对比
  9. jQuery开发插件的两个方法 js 深浅拷贝
  10. Regexp:常用的几个正则表达式