当前位置:   article > 正文

C++实现二叉树的创建和遍历_c++二叉树的建立

c++二叉树的建立

任务

1、实现二叉树的创建,存储结构为二叉链表结点类型

2、创建后实现先序中序后序的遍历结果

定义二叉树类和遍历时所需的栈

        二叉树类:一个 char 变量用来放数据,两个指针变量用来放左右孩子地址

  1. #include <iostream>
  2. using namespace std;
  3. class node {//定义二叉树类
  4. public:
  5. char data;
  6. node* leftchild;
  7. node* rightchild;
  8. };
  9. class stack {//定义栈
  10. public:
  11. char data;
  12. stack* next;
  13. };

定义压栈出栈函数

        压栈函数传入栈顶地址和一个数据,出栈函数仅需传入栈顶地址

  1. void push(stack*& stack1,char data) {//压栈
  2. stack* top = NULL;
  3. top = new stack;
  4. top->data = data;
  5. top->next = stack1;
  6. stack1 = top;
  7. }
  8. void pop(stack*& stack1) {//出栈
  9. cout << stack1->data;
  10. stack1 = stack1->next;
  11. }

定义创建二叉链表

        判断正在创建的结点是否超出想要创建的二叉树的结点数,如果超出则断开,没有超出就将数据存入新结点。然后决定新结点应放在头结点的左孩子还是右孩子,本代码的方法是:如果左孩子为空,就放左孩子,否则放右孩子。然后递归循环,直到结点创建完毕。

  1. void creat(node*head,char* a,int amount,int number) {//递归创建二叉表
  2. node* node1 = NULL;
  3. node1 = new node;
  4. if (number > amount) {//如果正在创建的结点不属于给定的数据,则跳过此次调用
  5. return;
  6. }
  7. node1->data = a[number-1];//储存数据进data
  8. if (head->leftchild == NULL) {//如果leftchild有结点了,则将正在创建的结点的地址给rightchild,否则给leftchild
  9. head->leftchild = node1;
  10. }
  11. else
  12. {
  13. head->rightchild = node1;
  14. }
  15. node1->leftchild = new node;
  16. node1->rightchild = new node;
  17. node1->leftchild = NULL;
  18. node1->rightchild = NULL;
  19. creat(node1, a,amount, 2 * number);//创建左孩子
  20. creat(node1, a, amount,2 * number + 1);//创建右孩子
  21. }

遍历函数

先序遍历

        如果结点为空或储存的是 # 就跳过,否则直接输出数据,然后递归循环。

  1. void first(node*head) {//先序遍历
  2. if (head == NULL) {//如果为空则跳过,否则输出data
  3. return;
  4. }
  5. if (head->data == '#') {//遇到#就跳过
  6. return;
  7. }
  8. cout << head->data;//不用压栈直接在函数里就cout
  9. first(head->leftchild);
  10. first(head->rightchild);
  11. }

中序遍历

        先判断数据是否为 #,是就跳过,否则先将数据压栈,然后判断左孩子是否为空,如果不为空则递归循环,否则出栈(左孩子的值),再出栈(根节点的值),然后递归。

  1. void second(node*head,stack*stack1) {//中序遍历
  2. if (head->data == '#') {//遇到#就跳过
  3. return;
  4. }
  5. push(stack1, head->data);//先压栈再判断孩子是否为空
  6. if (head->leftchild != NULL) {//如果左孩子不为空则将左孩子递归调用,
  7. second(head->leftchild, stack1);
  8. }
  9. else//否则出栈
  10. {
  11. pop(stack1);
  12. return;
  13. }
  14. pop(stack1);//因为左孩子已遍历,所以再出一个栈(根结点)
  15. second(head->rightchild, stack1);//最后遍历右孩子
  16. }

后序遍历

  1. void third(node* head, stack* stack1) {//后序遍历
  2. if (head->data == '#') {//遇到#就跳过
  3. return;
  4. }
  5. push(stack1, head->data);//先压栈再判断左右孩子是否为空
  6. if (head->leftchild != NULL) {//第一判断左孩子是否为空
  7. third(head->leftchild, stack1);
  8. }
  9. if (head->rightchild != NULL) {//第二判断右孩子是否为空
  10. third(head->rightchild, stack1);
  11. }
  12. pop(stack1);//最后再出根结点
  13. }

 主函数

  1. int main() {
  2. char a[500]{}; node* head = NULL; int amount = 0;
  3. head = new node; head->leftchild = NULL;
  4. stack* stack = NULL;
  5. cout << "请输入要储存的数组(结点为空写作#,数组结尾用?):" << endl;
  6. for (int i = 0; i < 500; i++)
  7. {
  8. cin >> a[i];
  9. amount++;
  10. if (a[i] == '?' ) {
  11. amount--;
  12. break;
  13. }
  14. }
  15. creat(head, a, amount,1);//创建二叉链表
  16. head = head->leftchild;//因为使用层次创建法,二叉表真正的头结点是leftchild,在此转换
  17. cout << "先序遍历结果为:";
  18. first(head); cout << endl;
  19. cout << "中序遍历结果为:";
  20. second(head, stack); cout << endl;
  21. cout << "后序遍历结果为:";
  22. third(head, stack); cout << endl;
  23. }

声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/知新_RL/article/detail/557743
推荐阅读
相关标签
  

闽ICP备14008679号