题目截图

中序遍历是左根右的顺序,当访问左结点时,左节点可以看成一个左子树的根节点,依然按照左根右的顺序遍历。同理,右结点也是。直到遍历完整个二叉树。整个过程都在递归。
- class Solution:
- def inorderTraversal(self, root: Optional[TreeNode]) -> List[int]:
- self.result = []
- if root == None:
- return self.result
- self.result = self.inorderTraversal(root.left) + [root.val] \
- + self.inorderTraversal(root.right)
- return self.result
时间复杂度:
空间复杂度:
- from typing import Optional,List
-
- class TreeNode:
- def __init__(self, val=0, left=None, right=None):
- self.val = val
- self.left = left
- self.right = right
-
- class Solution:
- def inorderTraversal(self, root: Optional[TreeNode]) -> List[int]:
- self.result = []
- if root == None:
- return self.result
- self.result = self.inorderTraversal(root.left) + [root.val] \
- + self.inorderTraversal(root.right)
- return self.result
-
-
- class main:
- a = Solution()
- root3 = TreeNode(3, left=None, right=None)
- root2 = TreeNode(2, left=root3, right=None)
- root = TreeNode(1, left = None, right= root2)
-
-
- b = a.inorderTraversal(root)
- print(b)
-
-
- if __name__ == '__main__':
- main()
LeetCode只需要写题目算法部分不需要写完整的实现部分。本题给出的条件是输入为root = [1,null,2,3],而本解答给出的完整实现的方法是利用TreeNode一个一个的添加节点。如果要直接使用 root = [1,null,2,3]作为输入条件需要再写一个有序列表转换为二叉树的算法。
方法二:迭代法
建立一个栈,然后遍历二叉树。
两层循环
内层循环:将二叉树的根节点一直和左节点存入栈中。然后指针左移, 将左节点的左子节点存入栈中,只要指针指向的结点存在就一直重复此动作,直到指针指向为空。
外层循环:然后出栈一个节点,将该节点的值填入输出结果中,并将指针指向该出栈结点的右节点。
以此完成左根右的中序遍历。
- class Solution:
- def inorderTraversal(self, root: Optional[TreeNode]) -> List[int]:
- if root == None:
- return []
-
- result, stack = list(), list()
- current = root
- while current or len(stack):
- while current:
- stack.append(current)
- current = current.left
- node = stack.pop()
- result.append(node.val)
- current = node.right
- return result
这种方式的迭代法又两层循环,复杂度较高。
还是按照这个思路,内外循环改为判断。
- class Solution:
- def inorderTraversal(self, root: Optional[TreeNode]) -> List[int]:
- if root == None:
- return []
-
- result, stack = [], []
- while root or stack:
- if root:
- stack.append(root)
- root = root.left
- else:
- cur = stack.pop()
- result.append(cur.val)
- root = cur.right
-
- return result
时间复杂度:
空间复杂度:
一、如果
无左孩子,先将
的值加入答案组,再访问
的右孩子,即
。
二、如果
有左孩子,则找到
左子树上最右的结点(即左子树中序遍历的最后一个结点),记为
。根据
的右孩子是否为空进行如下操作。
(1)如果
的右孩子为空,则将其右孩子指向
,然后访问
的左孩子,即
。
(2)如果
的右孩子不为空,则此时右孩子已经指向
,说明已经遍历完
的左子树,将
的右孩子置空,将
的值加入答案数组,然后访问
的右孩子,即
。
三、重复上述操作,直至访问完整棵树。
- class Solution:
- def inorderTraversal(self, root: Optional[TreeNode]) -> List[int]:
- result = []
- current, prev = root, None
- while current:
- if not current.left:
- result.append(current.val)
- current = current.right
- else:
- prev = current.left
- while prev.right and prev.right != current:
- prev = prev.right
- if not prev.right:
- prev.right = current
- current = current.left
- else:
- prev.right = None
- result.append(current.val)
- current = current.right
- return result
时间复杂度
空间复杂度
参看力扣官方解析