lintcode 二叉树的锯齿形层次遍历 (双端队列)

题目链接:

  http://www.lintcode.com/zh-cn/problem/binary-tree-zigzag-level-order-traversal/

二叉树的锯齿形层次遍历

  给出一棵二叉树,返回其节点值的锯齿形层次遍历(先从左往右,下一层再从右往左,层与层之间交替进行)

样例

  给出一棵二叉树 {3,9,20,#,#,15,7},

      3
     /     9  20
      /       15   7

  返回其锯齿形的层次遍历为:

  [
    [3],
    [20,9],
    [15,7]
  ]

思路:

  我们用双端队列模拟一下这个过程:开始的时候是正向遍历,3通过push_front()放入队列Q, 形成Q[3]。接着我们规定正向遍历的时候从队列前端去元素,下一层元素放入队列的时候是放入队列的后端;而反向遍历的时候正好相反,唯一不同的就是反向遍历时,下一层的右孩子结点(如果有)先放入队列的前端。

  开始Q[3](从前端取数字), 然后下一层放入后是Q[9,20](从后端去数字),20的下一层放入后是Q[15,7,9], 然后变成Q[15,7](从前端去数字),最后得到遍历的结果。

代码实现:

/**
 * Definition of TreeNode:
 * class TreeNode {
 * public:
 *     int val;
 *     TreeNode *left, *right;
 *     TreeNode(int val) {
 *         this->val = val;
 *         this->left = this->right = NULL;
 *     }
 * }
 */

class Solution {
    /**
     * @param root: The root of binary tree.
     * @return: A list of lists of integer include
     *          the zigzag level order traversal of its nodes‘ values
     */
public:
    vector<vector<int>> zigzagLevelOrder(TreeNode *root) {
        // write your code here
        vector<vector<int>> vv;
        if(root == NULL) return vv;
        deque<TreeNode *> q;
        q.push_back(root);
        bool dir = true;//true表示从左向右存储层次遍历,否则是从右向左
        int levelCnt = 1;//上一层的节点数目
        int curLevelCnt = 0;//下一层节点数目
        vector<int> v;
        while(!q.empty()){
            TreeNode *cur;
            if(dir){
                cur = q.front();
                q.pop_front();
            } else {
                cur = q.back();
                q.pop_back();
            }
            if(dir){
                if(cur->left){
                    q.push_back(cur->left);
                    ++curLevelCnt;
                }
                if(cur->right){
                    q.push_back(cur->right);
                    ++curLevelCnt;
                }
            } else {
                if(cur->right){
                    q.push_front(cur->right);
                    ++curLevelCnt;
                }
                if(cur->left){
                    q.push_front(cur->left);
                    ++curLevelCnt;
                }
            }
            v.push_back(cur->val);
            --levelCnt;
            if(levelCnt == 0){//这一层完毕
                vv.push_back(v);
                v.clear();
                levelCnt = curLevelCnt;
                curLevelCnt = 0;
                dir = !dir;
            }
        }
        return vv;
    }
};
时间: 2024-08-04 15:02:00

lintcode 二叉树的锯齿形层次遍历 (双端队列)的相关文章

LeetCode 103. 二叉树的锯齿形层次遍历(Binary Tree Zigzag Level Order Traversal)

103. 二叉树的锯齿形层次遍历 103. Binary Tree Zigzag Level Order Traversal 题目描述 给定一个二叉树,返回其节点值的锯齿形层次遍历.(即先从左往右,再从右往左进行下一层遍历,以此类推,层与层之间交替进行). LeetCode103. Binary Tree Zigzag Level Order Traversal中等 例如: 给定二叉树 [3,9,20,null,null,15,7], 3 / 9 20 / 15 7 返回锯齿形层次遍历如下: [

LeetCode 103 二叉树的锯齿形层次遍历 以及 LinkedList

LeetCode103 二叉树的锯齿形层次遍历: 给定一个二叉树,返回其节点值的锯齿形层次遍历.(即先从左往右,再从右往左进行下一层遍历,以此类推,层与层之间交替进行). 例如:给定二叉树 [3,9,20,null,null,15,7], 3 / \ 9 20 / \ 15 7返回锯齿形层次遍历如下:[[3],[20,9],[15,7]] import java.util.List; import java.util.ArrayList; import java.util.LinkedList;

leetcode 103. 二叉树的锯齿形层次遍历

给定一个二叉树,返回其节点值的锯齿形层次遍历.(即先从左往右,再从右往左进行下一层遍历,以此类推,层与层之间交替进行). 例如:给定二叉树 [3,9,20,null,null,15,7], 3 / 9 20 / 15 7 返回锯齿形层次遍历如下: [ [3], [20,9], [15,7] ] 1 class Solution { 2 public: 3 vector<vector<int>> zigzagLevelOrder(TreeNode* root) { 4 stack&l

LeetCode 第103题 二叉树的锯齿形层次遍历

给定一个二叉树,返回其节点值的锯齿形层次遍历.(即先从左往右,再从右往左进行下一层遍历,以此类推,层与层之间交替进行). 例如:给定二叉树 [3,9,20,null,null,15,7], 3 / 9 20 / 15 7 返回锯齿形层次遍历如下: [ [3], [20,9], [15,7] ] 思路: 与层次遍历类似,可以直接将特定层次的结果倒置 1 class Solution103 { 2 3 public List<List<Integer>> zigzagLevelOrde

【python-leetcode103-树的宽度遍历】二叉树的锯齿形层次遍历

给定一个二叉树,返回其节点值的锯齿形层次遍历.(即先从左往右,再从右往左进行下一层遍历,以此类推,层与层之间交替进行). 例如:给定二叉树 [3,9,20,null,null,15,7], 3 / \ 9 20    / \  15 7返回锯齿形层次遍历如下: [ [3], [20,9], [15,7]] 代码: # Definition for a binary tree node. # class TreeNode: # def __init__(self, x): # self.val =

8、泛型程序设计与c++标准模板库2.3双端队列容器

双端队列容器是一种放松了访问权限的队列.除了从队列的首部和尾部访问元素外,标准的双端队列也支持通过使用下标操作符"[]"进行直接访问. 它提供了直接访问和顺序访问方法.其头文件为<deque>. 1)双端队列容器的构造函数 有4中形式的构造函数: deque();//构造size()为0的双端队列容器 deque(size_type n,const T& v=T());//初始化大小为n的双端队列,第二个参数是每个元素的初始值,默认为T()构造的对象 deque(c

算法导论之八(10.1-5单数组实现双端队列)

算法导论第三版P131 题目: 10.1-5 栈插入和删除元素只能在同一端进行,队列的插入操作和删除操作分别在两端进行,与它们不同的,有一种双端队列(deque),其插入和删除操作都可以在两端进行.写出4个时间均为O(1)的过程,分别实现在双端队列插入和删除元素的操作,该队列使用一个数组实现的. 注意点: 1.左右端点指向的位置是类似于队列中的tail端点,是下一个插入操作的位置. 2.然后注意遍历的时候,左端点和右端点的位置关系,有两种可能,所以遍历的方式不一样. 代码: /* * 使用单数组

队列的应用:双端队列

双端队列(Deque:double ended queue)就是一个两端都是结尾的队列.队列的每一端都可以插入数据项和移除数据项.相对于普通队列,双端队列的入队和出队操作在两端都可进行. 双端队列的示意图: left:左端    right:右端 这里我们使用最常用的顺序结构来存储双端队列,为了节省空间,把它首尾相连,构成循环队列.并且规定left指向左端的第一个元素,right指向右端的下一个位置.那么队空的判断则是left==right,队满是(left-1+MAX)%MAX==right或

stl之deque双端队列容器

deque与vector很相似,不仅能够在尾部插入和删除元素,还能够在头部插入和删除. 只是当考虑到容器元素的内存分配策略和操作性能时.deque相对vector较为有优势. 头文件 #include<deque> 创建deque对象 1)deque();//创建一个没有不论什么元素的deque对象. deque<int> d 2)deque(size_typen);//创建一个具有n个元素的deque对象.每一个元素採用它的类型下的默认值. deque<int> d(