1 后序遍历
完成int* preorderTraversal(struct TreeNode* root, int* returnSize)
函数,使其可以实现前序遍历的功能
题目链接:https://leetcode-cn.com/problems/binary-tree-postorder-traversal/
1.1 递归实现
int getSize(struct TreeNode* root){
if(root == NULL)
return 0 ;
return getSize(root->left) + getSize(root->right) + 1;
}
void postOrder(struct TreeNode* root , int* arr , int* idx){
if(root){
postOrder(root->left , arr , idx);
postOrder(root->right , arr , idx);
arr[*idx] = root->val;
(*idx)++;
}
}
int* postorderTraversal(struct TreeNode* root, int* returnSize){
int sz = getSize(root);
int* arr = (int*)malloc(sizeof(int)*sz);
int idx = 0;
postOrder(root , arr , &idx);
*returnSize = idx;
return arr ;
}
1.2 非递归实现
1.2.1 基本思想
- 以节点开始,遍历最左路径,遇到的每一个节点,入栈
- 获取栈顶元素:
当前栈顶是否可以访问:
a:没有右子树:可以访问
b:右子树访问完成,可以访问
c:有右子树,但是还没有访问,不能访问当前元素,应首先访问右子树 - 结束:节点为空&&栈为空
1.2.2 程序代码
引入栈的定义及接口:
typedef struct TreeNode* STDataType;
typedef struct Stack {
STDataType* data; //数组
int top; //栈顶指针
int capacity; //数组的容量
}Stack;
//动态数组实现栈
void stackInit(Stack* st) {
if (st == NULL)
return;
st->data = NULL;
//栈中没有存储任何元素,栈顶指向-1
st->top = -1;
st->capacity = 0;
}
void checkCapacity(Stack* st) {
if (st == NULL)
return;
//若数组存储满了,则进行扩容
if (st->top == (st->capacity) - 1) {
int newCapacity = st->capacity == 0 ? 1 : st->capacity * 2;
//将st->data数组扩容到sizeof(STDataType)*newCapacity个字节大小
st->data = (STDataType*)realloc(st->data, sizeof(STDataType)*newCapacity);
st->capacity = newCapacity;
}
}
void stackPush(Stack* st, STDataType val) {
if (st == NULL)
return;
//检查栈是否满了
checkCapacity(st);
//进行入栈,栈顶+1 ,存入数据
st->top++;
st->data[st->top] = val;
}
void stackPop(Stack* st) {
//若栈中无数据则进行返回
if (st == NULL || st->top == -1) {
return;
}
//栈顶-1
st->top--;
}
//获取栈顶元素
STDataType stackTop(Stack* st) {
//前提是栈中有有效元素
return st->data[st->top];
}
//获取栈中的有效元素个数
int stackSize(Stack* st) {
if (st == NULL)
return 0;
return (st->top) + 1;
}
//检测栈是否为空,如果为空返回非零结果,如果不为空返回0
int stackEmpty(Stack* st) {
if (st == NULL || st->top == -1)
return 1;
return 0;
}
//销毁栈
void stackDestroy(Stack* st) {
free(st->data);
st->data = NULL;
st->top = -1;
st->capacity = 0;
}
实现后序遍历:
int getSize(struct TreeNode* root) {
if (root == NULL)
return 0;
return getSize(root->left) + getSize(root->right) + 1;
}
int* postorderTraversal(struct TreeNode* root, int* returnSize){
int sz = getSize(root);
int* arr = (int*)malloc(sizeof(int) * sz);
int idx = 0;
Stack st;
stackInit(&st);
struct TreeNode* prev = NULL;
while (root || !stackEmpty(&st)) {
while(root){
stackPush(&st , root);
root = root->left ;
}
struct TreeNode* top = stackTop(&st);
//没有右子树,或者右子树已经访问过,可以访问节点
if(top->right == NULL || prev == top->right){
arr[idx] = top->val;
idx++;
stackPop(&st);
prev = top ;
}else{
root = top->right ;
}
}
*returnSize = idx;
return arr;
}