二叉树层次建树

function.h代码如下

//
// Created by legion on 2024/3/5.
//

#ifndef INC_14_4_TREE_FUNCTION_H
#define INC_14_4_TREE_FUNCTION_H
#include <stdio.h>
#include <stdlib.h>

typedef char BiElemType;
typedef struct BiTNode{
    BiElemType c;
    struct BiTNode *lchild;
    struct BiTNode *rchild;
}BiTNode,*BiTree;

//tag结构体是辅助队列使用的 队列是由链表实现的
typedef struct tag{
    BiTree p;//树的某一个结点的地址值
    struct tag *pnext;
}tag_t,*ptag_t;//这个链表结构体类型tag_t 为什么和结构体名不一致

#endif //INC_14_4_TREE_FUNCTION_H

下面是main.cpp代码:

#include "function.h"

int main() {
    BiTree pnew;//用来指向新申请的树结点 结构体指针类型
    BiTree tree=NULL;//tree是指向树根的,代表树
    char c;
    //定义队列 phead是队列头ptail是队列尾 listpnew指向新结点 pcur是指向当前父结点
    ptag_t phead=NULL,ptail=NULL,listpnew=NULL,pcur;
    //输入abcdefghij
    while(scanf("%c",&c))
    {
        if(c=='\n')
        {
            break;//读取换行结束
        }
        //calloc申请的空间大小是两个参数直接相乘,并对空间进行初始化,赋值为0
        pnew= (BiTree)calloc(1,sizeof(BiTNode));
        pnew->c=c;//数据放进去
        listpnew= (ptag_t)calloc(1,sizeof(tag_t));//给队列结点申请空间
        listpnew->p=pnew;
        if(NULL==tree)//如果树为空 放进去即为树根
        {
            tree=pnew;//树的根
            phead=listpnew;//队列头
            ptail=listpnew;//队列尾
            pcur=listpnew;
            continue;
        } else{
            ptail->pnext=listpnew;//新结点放入链表 通过尾插法
            ptail=listpnew;//ptail指向队列尾部
        }//pcur始终指向要插入的结点的位置
        if(NULL==pcur->p->lchild)
        {
            pcur->p->lchild=pnew;//把新结点放到要插入结点的左边
        } else if(NULL==pcur->p->rchild)
        {
            pcur->p->rchild=pnew;//把新结点放到要插入结点的右边
            pcur=pcur->pnext;//左右都放了结点后,pcur指向队列下一个
        }
    }

    return 0;
}

listpnew->p = pnew;

这行代码的含义是将指向新创建的树结点 pnew 的指针赋给 listpnew 结点中的指针 p。这个 listpnew 结点实际上是一个辅助队列结点,而 pnew 则是树结点。

所以,listpnew->p 指向了最新创建的树结点 pnew。当使用 pcur->p 时,实际上是在引用这个指针,表示当前要插入新结点的位置。

注意,这里的 p 不是树结点的值,而是指向树结点的指针。因此,在 if(NULL==pcur->p->lchild) 中,pcur->p 表示当前要插入新结点的位置的树结点,而 lchildrchild 分别表示左子树和右子树。这里的 pcur->p->lchild 表示当前要插入新结点的位置的树结点的左子树是否为空,用于确定新结点应该插入的位置。

段代码中,listpnew->p 存储了指向新创建的树结点 pnew 的指针。由于 listpnew 是一个辅助队列结点,它的 p 指针确实是用来存储树结点的指针的。

因此,当我们需要引用树结点 pnew 的指针时,我们通过 listpnew->p 来获取。这样做的目的是为了在队列中维护一个顺序,确保新创建的树结点按照输入的顺序被插入到树中。

在这个特定的代码片段中,listpnew->p 的值即为最新创建的树结点的指针,而 pcur->p 在不同的时刻指向队列中当前要插入新结点的位置。这个位置可能是某个树结点的左子树或右子树。

代码中,辅助队列结构体中的指针 p 用于指向新创建的树结点,因此只能通过 listpnew->p 来获取新树结点的指针。(辅助队列为了获取新的树的指针 只能由自己的新队列结构体指针指向自己结构体中定义的树指针p来获取)

这种设计的目的是为了维护一个队列,确保树结点按照输入的顺序被插入。当你需要引用新创建的树结点时,通过 listpnew->p 就可以获取到最新的树结点指针。这种方式在构建树结构时保持了顺序,便于按照输入的先后顺序进行操作。

如果队列结构体中没有存储指向树结点的指针,那么就无法追踪最新的树结点,而这对于按顺序构建树结构是很重要的。


最终解释:

代码中,pcur 是用来迭代遍历队列的节点,而 pcur->p 是指向树节点的父节点。因此,通过 pcur->p->lchildpcur->p->rchild 才能准确访问树节点的左孩子或右孩子。

  1. pcur 是队列中的节点,通过 pcur->p 可以访问到树节点,因为 pcur->p 是指向树节点的指针。

  2. 在树节点的结构体中,包含了 lchildrchild 成员,用于表示左孩子和右孩子。

  3. 因此,为了访问树节点的左孩子,需要使用 pcur->p->lchild,其中 pcur->p 指向树节点,然后通过 ->lchild 访问左孩子。

这样的结构是为了正确表示二叉树的层次关系,确保在队列中迭代时能够访问到正确的父节点,从而插入新的节点。

代码中,pcur 是用来迭代遍历队列的节点,而 pcur->p 是指向树节点的父节点。因此,通过 pcur->p->lchildpcur->p->rchild 才能准确访问树节点的左孩子或右孩子。

让我进一步说明一下:

  1. pcur 是队列中的节点,通过 pcur->p 可以访问到树节点,因为 pcur->p 是指向树节点的指针。

  2. 在树节点的结构体中,包含了 lchildrchild 成员,用于表示左孩子和右孩子。

  3. 因此,为了访问树节点的左孩子,需要使用 pcur->p->lchild,其中 pcur->p 指向树节点,然后通过 ->lchild 访问左孩子。

这样的结构是为了正确表示二叉树的层次关系,确保在队列中迭代时能够访问到正确的父节点,从而插入新的节点。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

陆小果不会写代码

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值