【leetcode】二叉树的锯齿形层次遍历

问题描述:

给定一个二叉树,返回其节点值的锯齿形层次遍历。(即先从左往右,再从右往左进行下一层遍历,以此类推,层与层之间交替进行)。

例如:
给定二叉树 [3,9,20,null,null,15,7],

    3
   / \
  9  20
    /  \
   15   7

返回锯齿形层次遍历如下:

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

解题思路:

1、首先计算出树的高度depth,可以使用递归的方法求解,高度主要用于声明返回数组的行数,也就是给定函数头中的int* returnSize的值;

2、声明返回的数组变量:    int **result=(int **)malloc(sizeof(int *)*depth);//按要求存放每层节点的数字

3、声明临时存储tree每层节点的数组变量,因为存储的是指向节点的指针,所以声明如下:struct TreeNode*** temp=(struct TreeNode ***)malloc(sizeof(struct TreeNode**)*depth);

4、根据题目要求,开始逐行遍历节点,可以看出,奇数行是从右往左遍历,偶数行是从左往右遍历(从0开始计数)。

提交代码如下:

/**
 * Definition for a binary tree node.
 * struct TreeNode {
 *     int val;
 *     struct TreeNode *left;
 *     struct TreeNode *right;
 * };
 */
/**
 * Return an array of arrays of size *returnSize.
 * The sizes of the arrays are returned as *columnSizes array.
 * Note: Both returned array and *columnSizes array must be malloced, assume caller calls free().
 */

int getDepth(struct TreeNode* root)
{
    if(root==NULL)
    {
        return 0;
    }
    int leftDepth=getDepth(root->left);
    int rightDepth=getDepth(root->right);
    int depth=leftDepth>rightDepth?leftDepth:rightDepth;
    return depth+1;
}

int** zigzagLevelOrder(struct TreeNode* root, int** columnSizes, int* returnSize) {
    if(root==NULL)
    {
        return NULL;
    }
    int depth=getDepth(root);
    *returnSize=depth;//树的高度,即返回数组的行数
    int **result=(int **)malloc(sizeof(int *)*depth);//按要求存放每层节点的数字
    *columnSizes=(int *)malloc(sizeof(int)*depth);//树的每行的节点个数
    result[0]=(int *)malloc(sizeof(int));
    result[0][0]=root->val;
    (*columnSizes)[0]=1;
    
    struct TreeNode*** temp=(struct TreeNode ***)malloc(sizeof(struct TreeNode**)*depth);
    temp[0]=(struct TreeNode**)malloc(sizeof(struct TreeNode*));
    temp[0][0]=root;
    
    int i=0;
    for(i=0;i<depth-1;i++)//i表示当前树的层号,从0开始计数,注意i<depth-1,因为最后1行节点都没有子节点,不需要再遍历了,如果i<depth,会报如下错误:free(): invalid next size (fast): 0x0000000001d294d0 *** ---因为声明result或者temp数组的行树只有depth,如果i=depth-1继续执行,则result或者temp会继续分配一行,超出了声明的行数,因此指针被污染了。
    {
        int tempLen=(*columnSizes)[i]*2;//第i+1行的节点个数的最大值
        temp[i+1]=(struct TreeNode **)malloc(sizeof(struct TreeNode*)*tempLen);//临时存放第i+1行节点的数组
        (*columnSizes)[i+1]=0;
 
        result[i+1]=(int *)malloc(sizeof(int)*tempLen);//存放第i+1行节点的值

        int nodes=(*columnSizes)[i];
        int j=0;
        if(i%2==0)//如果i是偶数,那么下一行应该从右往左遍历
        {            
            for(j=nodes-1;j>=0;j--)
            {
                if(temp[i][j]->right!=NULL)
                {
                    result[i+1][(*columnSizes)[i+1]]=temp[i][j]->right->val;
                    temp[i+1][(*columnSizes)[i+1]++]=temp[i][j]->right;
                }
                if(temp[i][j]->left!=NULL)
                {
                    result[i+1][(*columnSizes)[i+1]]=temp[i][j]->left->val;
                    temp[i+1][(*columnSizes)[i+1]++]=temp[i][j]->left;
                }                
            }
        }
        else//如果i是奇数,那么下一行应该从左往右遍历
        {
            for(j=nodes-1;j>=0;j--)
            {
                if(temp[i][j]->left!=NULL)
                {
                    result[i+1][(*columnSizes)[i+1]]=temp[i][j]->left->val;
                    temp[i+1][(*columnSizes)[i+1]++]=temp[i][j]->left;
                }                
                if(temp[i][j]->right!=NULL)
                {
                    result[i+1][(*columnSizes)[i+1]]=temp[i][j]->right->val;
                    temp[i+1][(*columnSizes)[i+1]++]=temp[i][j]->right;
                }
            }
        }
    }
    
    free(temp);
    
    printf("columnSize:");
    for(i=0;i<depth;i++)
    {
        printf("%d,",(*columnSizes)[i]);
    }
    printf("\n returnSize=%d\n",*returnSize);;
    
    return result;
}

猜你喜欢

转载自blog.csdn.net/y___y___/article/details/81807827
今日推荐