树的操作(三)

这篇博客详细介绍了树的属性操作,包括结点数目、高度和度数的计算,均采用递归方法实现。同时,讲解了树的层次遍历的原理和步骤,通过建立队列并逐层推进,能有效地按层次打印树的所有节点。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

树的属性操作

树的属性操作具体指的就是树中结点的数目,树的高度,树的度数等…
1.树中结点的数目
在这里插入图片描述
查找树中结点数目的操作是递归完成的,是递归就有递归出口,当结点为空或者结点的子链表长度为0时就为递归出口,上图就是递归公式的提炼,我们看到下图,要求出该树的结点数可以分为3个部分,count(B)表示求以B为根结点的树的结点数,count©表示求以C为根结点的树的结点数,count(D)表示求以D为根结点的树的结点数,看得count(A)的同时又用到count©这就是一个递归调用的过程
在这里插入图片描述
代码演示

int count(GTreeNode<T>* node)const
{
      int ret = 0;
      if(node!=NULL)
      {
         ret = 1;
         for(node->child.move(0);!node->child.end();node->child.next())
         {
            ret+=count(node->child.current());
         }
      }
      return ret;
}

结果:

13

2.树中的高度
在这里插入图片描述
求树中的高度也是递归调用的,树中的高度等于其子树的高度的最大值+1,递归公式如下所示
在这里插入图片描述

int height(GTreeNode<T>* node)const
{
    int ret = 0;
    if(node!=NULL)
    {

       for(node->child.move(0);!node->child.end();node->child.next())
       {
          int h= height(node->child.current());
          if(ret<h)
          {
              ret = h;
          }
       }
       ret = ret + 1;
    }
    return ret;
}

结果

4

3.树的度数
求树的度数也是递归进行的

树的层次遍历

树是非线性的数据结构,树的结点没有固定的编号方式,为通用树结构提供新的方法,快速遍历每一个结点,设计思路就是引入一个游标,在树中定义一个游标(GTreeNode*),遍历开始前将游标指向根结点(root()),获取游标指向的数据元素,通过结点中的child成员移动游标,具体思路如下图所示,
在这里插入图片描述
具体操作:
在这里插入图片描述
我们新建一个队列,begin时将根节点A加入队列,然后打印出根节点A的值,接着将将队列的头结点A提出队列并将根节点A的子节点B,C,D加入队列中,此时打印出B节点的值并将B节点提出队列,接着将B节点的字节点E,F加入队列…依次类推就能将树的节点按层次打印出来
begin

bool begin()
{
      bool ret = (root()!=NULL);//判断根节点是否为空
      if(ret)
      {
         m_queue.clear();//清除队列
         m_queue.add(root());//在队列中加入根节点
      }
      return ret;
  }

next

bool next()
{
    bool ret = (m_queue.length()>0);//判断队列长度是否大于0
    if(ret)
    {
       GTreeNode<T> *node = m_queue.front();//取出队列头节点
       m_queue.remove();//删除该头节点
       for(node->child.move(0);!node->child.end();node->child.next())//将删除头结点的子节点加入队列中
       {
           m_queue.add(node->child.current());
       }
    }
    return ret;
}

current

 T current()
{
    if(!end())
    {
        return m_queue.front()->value;//若没有结束则打印节点值
    }
    else
    {
        THROW_EXCEPTION(InvalidParamterException,"No value at current position....");
    }
}

end

bool end()
{
    return (m_queue.length()==0);
 }

测试代码:

int main()
{
  GTree<char> t;
  GTreeNode<char> *node = NULL;
  GTreeNode<char> root;
  t.insert('A',NULL);
  node = t.find('A');
  t.insert('B',node);
  t.insert('C',node);
  t.insert('D',node);

  node = t.find('B');
  t.insert('E',node);
  t.insert('F',node);

  node = t.find('E');
  t.insert('K',node);
  t.insert('L',node);

  node = t.find('C');
  t.insert('G',node);

  node = t.find('D');
  t.insert('H',node);
  t.insert('I',node);
  t.insert('J',node);


  node = t.find('H');
  t.insert('M',node);



  //cout<<t.degree()<<endl;


  for(t.begin();!t.end();t.next())
  {
      cout<<t.current()<<endl;
  }
  return 1;
}

结果:
在这里插入图片描述

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值