力扣算法:翻转二叉树

力扣算法:翻转二叉树

  • 一、力扣算法:翻转二叉树
    • 1、问题
    • 2、思路
    • 3、解题代码
    • 4、时间与空间复杂度
  • 备注

一、力扣算法:翻转二叉树

1、问题

翻转一棵二叉树。

示例1:

力扣算法:翻转二叉树_第1张图片

示例2:

力扣算法:翻转二叉树_第2张图片

2、思路

思路1:

采用“深度遍历-先序遍历”的思路。

  1. 递归的终止条件为“节点为null”。
  2. 交换当前节点的左右节点,再递归的交换当前节点的左节点,递归的交换当前节点的右节点。

思路2:

采用“广度遍历”的思路。

  1. 创建一个队列,将根结点放进去,不断迭代队列中元素。
  2. 每次从队列中取出一个节点。
  3. 左子树与右子树的位置互换。
  4. 分别判断左子树、右子树是否为空,不为空则放入队列中。

3、解题代码

1、解题代码:

#coding:utf-8
# Definition for a binary tree node.
from MyTool import Tree
class TreeNode:
    def __init__(self, val=0, left=None, right=None):
        self.val = val
        self.left = left
        self.right = right

class Solution:
	#采用“深度遍历-先序遍历”翻转二叉树
    def invertTree1(self, root1: TreeNode) -> TreeNode:
        if not root1:
            return None

        root1.left, root1.right = root1.right, root1.left
        self.invertTree1(root1.left)
        self.invertTree1(root1.right)
        return root1
        
	#采用“广度遍历”翻转二叉树
    def invertTree2(self, root2: TreeNode) -> TreeNode:
        if not root2:
            return None
        queue = [root2]
        while queue:
            tmp_node = queue.pop(0)
            tmp_node.left,tmp_node.right = tmp_node.right,tmp_node.left
            if tmp_node.left:
                queue.append(tmp_node.left)
            if tmp_node.right:
                queue.append(tmp_node.right)
        return root2



if __name__ == "__main__":
    global null
    null = None
    data = [4,2,7,1,3,6,9]
    #data = [1,2,2,null,3,null,3]

    #创建二叉树
    print("原始二叉树为:")
    tree1 = Tree().build_tree(data)
    print("\t")
    tree2 = Tree().build_tree(data)
    print("\t")

    #翻转二叉树
    solution=Solution()
    invert1 = solution.invertTree1(tree1)
    invert2 = solution.invertTree2(tree2)

    #打印翻转后的二叉树
    print("反转后的二叉树为:")
    Tree().show_tree(invert1)
    print("\t")
    Tree().show_tree(invert2)

2、解题中用到的“工具代码”:

#coding:utf-8

from typing import List
class TreeNode:
    def __init__(self, val=0, left=None, right=None):
        self.val = val
        self.left = left
        self.right = right

#创建二叉树
class Tree:
    def __init__(self):
        self.root = None

    def add(self,item):
        node = TreeNode(item)
        if self.root is None:
            self.root = node
            return
        queue = [self.root]

        while queue:
            cur_node = queue.pop(0)
            if cur_node.left is None:
                cur_node.left = node
                print("left{}".format(cur_node.left.val),end = " ")
                return
            else:
                queue.append(cur_node.left)
            if cur_node.right is None:
                cur_node.right = node
                print("right{}".format(cur_node.right.val),end = " ")
                return
            else:
                queue.append(cur_node.right)

    def build_tree(self,data:List):
        print("root{}".format(data[0]),end = " ")
        for i in data:
            self.add(i)
        return self.root



    def show_tree(self,root: TreeNode)-> None:
        print("root{}".format(root.val), end=" ")
        print("left{}".format(root.left.val), end=" ")
        print("right{}".format(root.right.val), end=" ")
        print("left{}".format(root.left.left.val), end=" ")
        print("right{}".format(root.left.right.val), end=" ")
        print("left{}".format(root.right.left.val), end=" ")
        print("right{}".format(root.right.right.val), end=" ")

if __name__ == "__main__":
    global null
    null = None
    data = [4,2,7,1,3,6,9]
    #data = [1,2,2,null,3,null,3]

    #创建二叉树
    tree = Tree().build_tree(data)

4、时间与空间复杂度

思路1:
时间复杂度:O(n)
访问每个元素。

空间复杂度:O(h)
最坏的情况下,需要存放 O(h)个函数调用(h是树的高度)。

思路2:
时间复杂度: O(n)
每个节点都需要入队列/出队列一次。

空间复杂度: O(n)
最坏的情况下会包含所有的叶子节点,完全二叉树叶子节点是 n/2个。

备注

解题中需注意的问题:

if 和 elif 的区别

  • 多个if语句是每次单独判断。

"""条件1和条件2是独立的。
第一次判断a的值小于6,所以打印出还可以;
第二次判断a的值小于20,所以打印出不考虑;
如果所有的if语句都判断失败,才会执行else后的语句,否则else语句不执行。"""

a = 5
if a < 6: #条件1
    print("还可以")
if a < 20: #条件2
    print("不考虑")
else:
    print("买买买")
    
#输出为:
#还可以
#不考虑
  • 如果条件2修改为elif,结果就不同了。
"""这次条件1和条件2是相关的。
也就是说,如果条件1判断成功的话,条件2就不会继续判断了。
反过来,如果条件1判断失败,那么就会继续判断条件2。
如果条件1和条件2都判断失败,那么则执行else里面的语句。"""
a = 5
if a < 6: #条件1
    print("还可以")
elif a < 20: #条件2
    print("不考虑")
else:
    print("买买买")
#输出为:
#还可以

你可能感兴趣的:(力扣算法,算法,二叉树,数据结构,python)