网站设计行业前景搜索引擎优化方法有哪些
目录
1. 二叉树的前序遍历
1.1 题目链接与描述
1.2 解题思路
1.3 程序
2. 二叉树中序遍历
2.1 题目链接与描述
2.2 解题思路
2.3 程序
3. 二叉树后序遍历
3.1 题目链接与描述
3.2 解题思路
3.3 程序
1. 二叉树的前序遍历
1.1 题目链接与描述
题目链接:
144. 二叉树的前序遍历 - 力扣(LeetCode)
题目描述:
给你二叉树的根节点 root
,返回它节点值的 前序 遍历。
1.2 解题思路
注意该题目与直接打印前序遍历结果的不同,该题目要求遍历结果存储到一个数组中进行打印:
遍历函数的大致实现思路与之前直接打印遍历结果的实现基本一致,只是需要将打印的语句修改为存入数组的语句。
同时需要为返回的数组开辟空间,为了实现空间的高效合理应用,需要考虑开辟大小问题;
为了实现正确的存储,需要设计下标指明下一个存储位置。
1.3 程序
/*** Definition for a binary tree node.* struct TreeNode {* int val;* struct TreeNode *left;* struct TreeNode *right;* };*/
/*** Note: The returned array must be malloced, assume caller calls free().*/
// 遍历二叉树确定动态开辟空间大小
int TreeSize(struct TreeNode* root) {return root == NULL ? 0 : TreeSize(root->left) + TreeSize(root->right) + 1;
}
// 前序遍历二叉树并按序存入数组
void PreOrder(struct TreeNode* root, int* a, int* pi) {if (root == NULL)return;a[(*pi)++] = root->val;PreOrder(root->left, a, pi);PreOrder(root->right, a, pi);
}
int* preorderTraversal(struct TreeNode* root, int* returnSize) {// returnSize为输出型参数*returnSize = TreeSize(root);int* a = (int*)malloc(sizeof(int) * (*returnSize));int i=0;PreOrder(root, a, &i);return a;
}
注意点:
1. 关于动态空间开辟的方式:
(1)可以采用之前顺序表的扩容方式,先malloc 4字节,随后再动态扩容;
(2)题目说明“树中节点数目在范围 [0, 100]
内”,可一次性扩容100字节,但可能造成浪费;
(3)遍历给定的二叉树,计算结点个数来确定要开辟的空间大小:
// 遍历二叉树确定动态开辟空间大小
int TreeSize(struct TreeNode* root) {return root == NULL ? 0 : TreeSize(root->left) + TreeSize(root->right) + 1;
}
2. 关于输出型参数:
要求实现的函数preorderTraversal中,除用于接收当前二叉树根结点指针变量struct TreeNode* root外,还有一个int*类型的参数 returnSize。
力扣oj对于返回值为数组的题目要求:除返回数组外,还需要返回数组的大小,故而给定一个输出型参数。为了保证调用函数能实现对数组尺寸的修改,将输出型参数定义为指针类型,通过在函数中解引用进行操作。
3. 关于数组下标i作为参数:
该题目中要求将前序遍历结果按序存到数组中,故而前序遍历函数中还需要一个数组下标参数i:
// 前序遍历二叉树并按序存入数组
void PreOrder(struct TreeNode* root, int* a, int i) {if (root == NULL)return;a[i++] = root->val;PreOrder(root->left, a, i);PreOrder(root->right, a, i);
}
上述写法是错误的,递归调用PreOrder时会出现元素覆盖问题,比如:
在3作为根结点的二叉树遍历中将i递增为1,递归调用其左子树,在1作为根结点的子树遍历中,将i递增为2,遍历完毕后返回到以3为根结点的二叉树的遍历函数中,再递归调用其右子树,此时就会出现本应将元素2存放至下标为2的位置上,但由于下标采用传值调用,使得将元素2存放至下标为1的位置处,导致元素覆盖,最终返回值为:[3,2,随机值]。
为了解决该问题,需要将数组下标参数设计为传址调用方式:
// 前序遍历二叉树并按序存入数组
void PreOrder(struct TreeNode* root, int* a, int* pi) {if (root == NULL)return;a[(*pi)++] = root->val;PreOrder(root->left, a, pi);PreOrder(root->right, a, pi);
}
2. 二叉树中序遍历
2.1 题目链接与描述
题目链接:
94. 二叉树的中序遍历 - 力扣(LeetCode)
题目描述:
给定一个二叉树的根节点 root
,返回 它的 中序 遍历 。
2.2 解题思路
与上题一致,仅需修改遍历函数的递归与将元素存入数组的顺序。
2.3 程序
/*** Definition for a binary tree node.* struct TreeNode {* int val;* struct TreeNode *left;* struct TreeNode *right;* };*/
/*** Note: The returned array must be malloced, assume caller calls free().*/
int TreeSize(struct TreeNode* root) {return root == NULL ? 0 : TreeSize(root->left) + TreeSize(root->right) + 1;
}
void InOrder(struct TreeNode* root, int* a, int* pi) {if (root == NULL)return;InOrder(root->left, a, pi);a[(*pi)++] = root->val;InOrder(root->right, a, pi);
}
int* inorderTraversal(struct TreeNode* root, int* returnSize) {*returnSize = TreeSize(root);int* a = (int*)malloc(sizeof(int) * (*returnSize));int i = 0;InOrder(root, a, &i);return a;
}
3. 二叉树后序遍历
3.1 题目链接与描述
题目链接:
145. 二叉树的后序遍历 - 力扣(LeetCode)
题目描述:
给你一棵二叉树的根节点 root
,返回其节点值的 后序遍历 。
3.2 解题思路
与上题一致,仅需修改遍历函数的递归与将元素存入数组的顺序。
3.3 程序
/*** Definition for a binary tree node.* struct TreeNode {* int val;* struct TreeNode *left;* struct TreeNode *right;* };*/
/*** Note: The returned array must be malloced, assume caller calls free().*/
int TreeSize(struct TreeNode* root){return root==NULL?0:TreeSize(root->left)+TreeSize(root->right)+1;
}
void PostOrder(struct TreeNode* root, int* a, int* pi){if(root==NULL)return;PostOrder(root->left, a, pi);PostOrder(root->right, a, pi);a[(*pi)++]=root->val;
}
int* postorderTraversal(struct TreeNode* root, int* returnSize) {*returnSize=TreeSize(root);int* a = (int*)malloc(sizeof(int)*(*returnSize));int i=0;PostOrder(root, a, &i);return a;
}