zoukankan      html  css  js  c++  java
  • 二叉树遍历

    二叉树遍历

      依据根节点的访问次序分为先序遍历、中序遍历、后序遍历、层序遍历。中序遍历即以左节点、根节点、右节点的顺序遍历,根节点放在中间,其它方式依此类推。下面介绍三种中序遍历算法。

    递归

      递归法简单明了,但是效率较低。下面为中序遍历,前序遍历和后序遍历同理。

    /**
     * Definition for a binary tree node.
     * struct TreeNode {
     *     int val;
     *     TreeNode *left;
     *     TreeNode *right;
     *     TreeNode(int x) : val(x), left(NULL), right(NULL) {}
     * };
     */
    
    void inorderTraversal(TreeNode* root, vector<int>& list){
        if(root != NULL){
            inorderTraversal(root->left, list);
            list.push_back(root->val);
            inorderTraversal(root->right, list);
        }
    }

    栈方法

    • 前序遍历

    vector<int> inorderTraversal(TreeNode* root) {
         vector<int> res;
            vector<TreeNode*> stk;
            TreeNode* cur = root;
            while(cur != NULL || stk.size() != 0){
                if(cur != NULL) {
                    res.push_back(cur->val);
                    stk.push_back(cur);
                    cur = cur->left;
                }
                else {
                    cur = stk.back();
                    stk.pop_back();
                    cur = cur->right;
                }
            }
            return res;
    }
    • 中序遍历

    vector<int> inorderTraversal(TreeNode* root) {
          vector<int> res;
            vector<TreeNode*> stk;
            TreeNode* cur = root;
            while(cur != NULL || stk.size() != 0){
                if(cur != NULL) {
                    stk.push_back(cur);
                    cur = cur->left;
                }
                else {
                    cur = stk.back();
                    res.push_back(cur->val);
                    stk.pop_back();
                    cur = cur->right;
                }
            }
            return res;
    }                        
    • 后续遍历

    vector<int> postorderTraversal(TreeNode* root) {
            vector<int> res;
            if(root == NULL) return res;
            stack<TreeNode*> tree;
            while(root != NULL || tree.size() != 0) {
                if(root != NULL) {
                    tree.push(root);
                    res.insert(res.begin(), root->val); //因为是后续遍历,节点需要从队头插入,并且先遍历右子树,加入的顺序是中-右-左,这样最终的顺序就是左-右-中
                    root = root->right;
                }
                else {
                    root = tree.top()->left;
                    tree.pop();
                }
            }
            return res;
        }

    莫里斯遍历

      该方法通过设置根节点作为其前驱节点的右孩子,来构造线索二叉树,这样在遍历完左子树时,遍历前驱结点的右孩子就可以跳转到根节点继续遍历右子树。下面是中序遍历实现,前序遍历通过更改res.push_back()的位置即可,后续遍历可以用上述思想,将前序遍历修改为头部插入,并且先遍历右子树。

    vector<int> inorderTraversal(TreeNode* root) {
            vector<int> res;
            TreeNode* pre;
            while(root){
                if(root->left){
                    pre = root->left;
                    while(pre->right && pre->right != root) pre = pre->right;
                    if(pre->right == NULL){  //说明root第一次作为当前根节点出现,其左子树没有遍历过,则为其前驱结点设置线索,进入左子树。
                        pre->right = root;
                        root = root->left;
                        continue;
                    }
              //说明root是通过前驱结点->right跳转到的,左子树已经遍历完成,需要删除线索,进入右子树。 pre
    ->right = NULL; res.push_back(root->val); root = root->right; } else{ res.push_back(root->val); root = root->right; } } return res; }
  • 相关阅读:
    mysql报错解决
    数据存储
    记录python接口自动化测试--把操作excel文件的方法封装起来(第五目)
    基础补充:使用xlrd模块读取excel文件
    记录python接口自动化测试--利用unittest生成测试报告(第四目)
    记录python接口自动化测试--pycharm执行测试用例时需要使用的姿势(解决if __name__ == "__main__":里面的程序不生效的问题)(第三目)
    记录python接口自动化测试--unittest框架基本应用(第二目)
    记录python接口自动化测试--requests使用和基本方法封装(第一目)
    连接数据后,当执行查询语句报错:ORA-01219: 数据库未打开: 仅允许在固定表/视图中查询
    通过运行一个tomcat容器来记录下初学docker常用的几个命令---容器篇
  • 原文地址:https://www.cnblogs.com/zz-zhang/p/inorderTraversal.html
Copyright © 2011-2022 走看看