数据结构之二叉树的一些基本操作

二叉树是树的特殊一种,具有如下特点:1、每个结点最多有两颗子树,结点的度最大为2。2、左子树和右子树是有顺序的,次序不能颠倒。3、即使某结点只有一个子树,也要区分左右子树。
头文件 BTree.h

#ifndef __BTREE_H__
#define __BTREE_H__#define BLEFT  0                 // 表示插入二叉树的左边
#define BRIGHT 1                 // 表示插入二叉树的右边#define TRUE   1
#define FALSE  0typedef char BTreeData;
// 二叉树的结点
typedef struct _btreeNode
{BTreeData data;struct _btreeNode* lchild;   // 指向左孩子结点的指针struct _btreeNode* rchild;   // 指向右孩子结点的指针
}BTreeNode;
// 二叉树
typedef struct _btree
{BTreeNode *root;             // 指向二叉树的根节点int  count;                  // 记录二叉树结点的个数
}BTree;
typedef void(*Print_BTree)(BTreeNode*);// 创建一棵二叉树
BTree* Create_BTree();// pos 走的路径 值类似 110(左右右)  011 (右右左)
// count 代表走的步数
// flag  代表被替换的结点应该插入在新节点的位置,如果是BLEFT 表示插在左边,BRIGHT表示插在右边
int Btree_Insert (BTree* tree, BTreeData data, int pos, int count, int flag);// 打印二叉树
void Display (BTree* tree, Print_BTree pfunc);// 删除pos处的结点
int Delete   (BTree* tree, int pos, int count);// 求树的高度
int BTree_Height  (BTree* tree);// 求树的度
int BTree_Degree  (BTree* tree);// 清除树
int BTree_Clear   (BTree* tree);// 销毁树
int BTree_Destroy (BTree** tree);// 打印
void printA (BTreeNode* node);// 前序遍历
void pre_order  (BTreeNode* node);// 中序遍历
void mid_order  (BTreeNode* node);// 后序遍历
void last_order (BTreeNode* node);#endif // __BTREE_H__

源文件 BTree.c

#include "BTree.h"
#include <stdlib.h>
#include <stdio.h>BTree *Create_BTree()
{BTree* btree = (BTree*) malloc(sizeof(BTree)/sizeof(char));if (NULL == btree){return NULL;}btree->count = 0;btree->root  = NULL;return btree;
}int Btree_Insert (BTree* tree, BTreeData data, int pos, int count, int flag)
{if (NULL == tree || (flag != BLEFT && flag != BRIGHT)){return FALSE;}BTreeNode* node = (BTreeNode*) malloc(sizeof(BTreeNode)/sizeof(char));if (NULL == node){return FALSE;}node->data   = data;node->lchild = NULL;node->rchild = NULL;// 找插入的位置BTreeNode *parent  = NULL;BTreeNode *current = tree->root;     // current 一开始指向根节点,根节点的父节点是空int way;                             // 保存当前走的位置while (count > 0 && current != NULL){way = pos &  1;                  // 取出当前走的方向pos = pos >> 1;                  // 移去走过的路线// 因为当前位置就是走完以后的位置的父节点parent = current;if (way == BLEFT)   // 往左走{current = current->lchild;}else{current = current->rchild;}count --;}// 把被替换掉的结点插入到新节点下面if (flag == BLEFT){node->lchild = current;}else{node->rchild = current;}// 把新节点插入到二叉树中,way保存了应该插入在父节点的左边还是右边if (NULL != parent){if (way == BLEFT){parent->lchild = node;}else{parent->rchild = node;}}else{tree->root = node;  // 替换根节点}tree->count++;return TRUE;
}void r_display (BTreeNode* node, Print_BTree pfunc, int gap)
{int i;if (node == NULL){for (i = 0; i < gap; i++){printf ("-");}printf ("\n");return;}for (i = 0; i < gap; i++){printf ("-");}// 打印结点// printf ("%c\n", node->data);pfunc (node);if (NULL != node->lchild || NULL != node->rchild){// 打印左孩子r_display (node->lchild, pfunc, gap+4);// 打印右孩子r_display (node->rchild, pfunc, gap+4);}
}void Display (BTree* tree, Print_BTree pfunc)
{if (tree == NULL){return;}r_display (tree->root, pfunc, 0);
}void r_delete (BTree* tree, BTreeNode* node)
{if (NULL == node || NULL == tree){return;}// 先删除左孩子r_delete (tree, node->lchild);// 删除右孩子r_delete (tree, node->rchild);free (node);tree->count--;
}int Delete (BTree* tree, int pos, int count)
{if (NULL == tree)return FALSE;// 找结点BTreeNode* parent  = NULL;BTreeNode* current = tree->root;int way;while (count > 0 && NULL != current){way = pos &  1;pos = pos >> 1;parent = current;if (way == BLEFT){current = current->lchild;}else{current = current->rchild;}       count--;}if (NULL != parent){if (way == BLEFT){parent->lchild = NULL;}else{parent->rchild = NULL;}}else{tree->root = NULL;}// 释放结点r_delete (tree, current);return TRUE;
}int r_height (BTreeNode* node)
{if (NULL == node){return 0;}int lh = r_height (node->lchild);int rh = r_height (node->rchild);return (lh > rh ? lh+1 : rh+1);
}int BTree_Height (BTree* tree)
{if (NULL == tree){return FALSE;}int ret = r_height (tree->root);return ret;
}int r_degree (BTreeNode* node)
{if (NULL == node){return 0;}int degree = 0;if (NULL != node->lchild){degree++;}if (NULL != node->rchild){degree++;}if (1 == degree){int ld = r_degree (node->lchild);if (2 == ld){return 2;}int rd = r_degree (node->rchild);if (2 == rd){return 2;}}return degree;
}int BTree_Degree (BTree* tree)
{if (NULL == tree){return FALSE;}int ret = r_degree (tree->root);return ret;
}int BTree_Clear (BTree* tree)
{if (NULL == tree){return FALSE;}Delete (tree, 0, 0);  // 删除根节点tree->root = NULL;return TRUE;
}int BTree_Destroy (BTree** tree)
{if (NULL == tree){return FALSE;}BTree_Clear (*tree);free (*tree);*tree = NULL;return TRUE;
}void pre_order  (BTreeNode* node)
{if (NULL == node){return;}printf    ("%4c", node->data);pre_order (node->lchild);pre_order (node->rchild);
}void mid_order  (BTreeNode* node)
{if (NULL == node){return;}mid_order (node->lchild);printf    ("%4c", node->data);mid_order (node->rchild);
}void last_order (BTreeNode* node)
{if (NULL == node){return;}last_order (node->lchild);  last_order (node->rchild);printf     ("%4c", node->data);
}void printA (BTreeNode* node)
{printf ("%c\n", node->data);
}

主函数 main.c

#include "BTree.h"
#include <stdio.h>int main()
{BTree* btree = Create_BTree();if (NULL == btree){printf ("创建失败\n");}else{printf ("创建成功\n");}Btree_Insert (btree, 'A', 0, 0, 0);Btree_Insert (btree, 'B', 0, 1, 0);Btree_Insert (btree, 'C', 1, 1, 0);Btree_Insert (btree, 'D', 0, 2, 0);Btree_Insert (btree, 'E', 2, 2, 0);Btree_Insert (btree, 'F', 0, 3, 0);Btree_Insert (btree, 'G', 4, 3, 0);Btree_Insert (btree, 'H', 3, 2, 0);Display (btree, printA);printf ("前序遍历:\n");pre_order (btree->root);printf ("\n");printf ("中序遍历:\n");mid_order (btree->root);printf ("\n");printf ("后序遍历:\n");last_order (btree->root);printf ("\n");#if 0Delete (btree, 0, 1);printf ("删除后--------------\n");Display (btree, printA);printf ("高度: %d\n", BTree_Height (btree));printf ("度 :  %d\n", BTree_Degree (btree));printf ("清空后--------------\n");BTree_Clear (btree);Display (btree, printA);BTree_Destroy (&btree);//btree = NULL;
#endif  return 0;
}

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/448513.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

【Arduino】使用C#实现Arduino与电脑进行串行通讯

在给Arduino编程的时候&#xff0c;因为没有调试工具&#xff0c;经常要通过使用串口通讯的方式调用Serial.print和Serial.println输出Arduino运行过程中的相关信息&#xff0c;然后在电脑上用Arduino IDE的Serial Monitor来查看print出来的信息。Serial Monitor不仅可以接受Ar…

虚拟机NAT模式联网

阿里开源镜像软件&#xff1a;https://opsx.alibaba.com/mirror 如何使VMware ip与本机ip处于同一网段 https://blog.csdn.net/kakuma_chen/article/details/71425620 转载于:https://www.cnblogs.com/cdy0626/p/11131440.html

VS2008下最新X264(svn 2009.9)编译不过的解决办法

总有人说最新的版本 编译不过&#xff0c;搞的群、 论坛里到处都是这种求助贴。建议斑竹把这个解决办法放到醒目的位置&#xff0c;以减少噪音。科普开始1、编译问题由于MS的VS编译器对C99标准支持不好&#xff0c;不支持函数当中混合定义、声明变量。解决办法&#xff1a;在函…

node、npm、vue安装 -- VUE 项目 demo 实例

前些天发现了一个巨牛的人工智能学习网站&#xff0c;通俗易懂&#xff0c;风趣幽默&#xff0c;忍不住分享一下给大家。点击跳转到教程。 1. 安装node&#xff1a; sudo yum install epel-release sudo yum install nodejs node --version // 安装好后查看版本2. 安装 npm …

用C语言实现简单的停车场管理

这个程序是利用栈和循环队列实现的&#xff0c;自己得先处理好逻辑关系就好了。由于题目没有要求&#xff0c;这个程序就没加重复判断&#xff0c;比如一辆车已经停在车位上或者便道上&#xff0c;再来一辆就判断不了了。关于栈&#xff0c;就是先进后出的思想&#xff0c;队列…

推荐一个配置linux服务的网站

该网站的各种linux服务的配置都是基于CentOS系统的 基本上各种linux服务都有了 http://www.server-world.info/en/转载于:https://www.cnblogs.com/Skyar/p/3582389.html

mariadb数据库增删改查

1.常用数据类型 1&#xff09;整数:int, bit 2&#xff09;小数:decimal    #decimal(5,2)表示共有五位数&#xff0c;保留两位小数 3&#xff09;字符串:varchar, char   4&#xff09;日期时间:date, time, datetime 5&#xff09;枚举类型(enu…

为什么你工作努力却没有起色?

成为职场达人&#xff0c;未必要经常挑灯夜战。相反&#xff0c;注意到下面几条&#xff0c;会让你少走弯路。 1&#xff09;成长的机会永远比眼前的待遇重要——做重要的事比多拿钱重要。 我知道在水木bbs上的worklife版本&#xff0c;每天都在上演的就是比较自己的第一个o…

《 Spring 实战 》(第4版) 读书笔记 (未完结,更新中...)

前些天发现了一个巨牛的人工智能学习网站&#xff0c;通俗易懂&#xff0c;风趣幽默&#xff0c;忍不住分享一下给大家。点击跳转到教程。 Pxx 表示在书的第 xx 页。 Spring 框架的核心是 Spring 容器。 1. (P7.) 构造器注入是依赖注入的方式之一。 紧耦合&#xff1a;在 …

数据结构排序法之希尔排序法(Shell Sort)

希尔排序&#xff0c;也叫递减增量排序&#xff0c;是插入排序的一种更高效的改进版本。希尔排序是不稳定的排序算法。 希尔排序是基于插入排序的以下两点性质而提出改进方法的&#xff1a; 1、插入排序在对几乎已经排好序的数据操作时&#xff0c;效率高&#xff0c;即可以达…

Windows To Ghost系统封装之必备软件集 - 好压

好压压缩软件&#xff08;HaoZip&#xff09;是强大的压缩文件管理器&#xff0c;是完全免费的新一代压缩软件&#xff0c;相比其它压缩软件系统资源占用更少&#xff0c;有更好的兼容性&#xff0c;压缩率比较高。 它提供了对ZIP、7Z和TAR文件的完整支持&#xff0c;能解压RAR…

js 弹窗并定时关闭

1. $(input).click(function() {prompt(点击成功, 2000) })function prompt(newName, time, fn) {var $div $(<div></div>);$div.css({position: fixed,top: 0,left: 0,width: 100%,height: 100%,z-index: 200,background-color: rgba(0,0,0,0.4),// background-c…

数据结构排序法之插入法

插入排序是一种简单直观的排序算法。它的工作原理非常类似于我们抓扑克牌。 对于未排序数据(右手抓到的牌)&#xff0c;在已排序序列(左手已经排好序的手牌)中从后向前扫描&#xff0c;找到相应位置并插入。 插入排序在实现上&#xff0c;通常采用in-place排序&#xff08;即…

XSLT学习笔记

1. 样式声明&#xff1a;<xsl:stylesheet>或<xsl:transform> 2. XSLT常用元素&#xff1a; 2.1 <xsl:template>&#xff1a;创建模板 Match属性的作用是使模板和XML元素相关联 e.g.:<xsl:template match"\">......</xsl:template&g…

职场:人生从没有最佳时机!一个离职客服人员的领悟

每个人都有感到失落迷惘的时候。 人生用专制又霸道的方式运行着&#xff0c;每当我们心想一切尘埃落定、生活稳固的时候&#xff0c;生活总爱给我们惊喜&#xff0c;粉碎我们短暂的安逸&#xff0c;让我们不得不重新思考。 「我走对路了吗?」 「我能够赚更多钱、爬到更高的地位…

VS Code 的常用快捷键

VS Code 的常用快捷键和插件 一、vs code 的常用快捷键 前些天发现了一个巨牛的人工智能学习网站&#xff0c;通俗易懂&#xff0c;风趣幽默&#xff0c;忍不住分享一下给大家。点击跳转到教程。 1、注释&#xff1a; a) 单行注释&#xff1a;[ctrlk,ctrlc] 或 ctrl/ b) 取消…

vue-axios interceptors

import axios from axios import cookie from js-cookie const options {baseURL: window.location.protocol process.env.BASE_API,headers: {},timeout: 20000 } const fetch axios.create(options)// request拦截器 fetch.interceptors.request.use(config > {if (coo…

数据结构排序法之鸡尾酒排序法he快速排序法

鸡尾酒排序&#xff0c;也叫定向冒泡排序&#xff0c;是冒泡排序的一种改进。此算法与冒泡排序的不同处在于从低到高然后从高到低&#xff0c;而冒泡排序则仅从低到高去比较序列里的每个元素。他可以得到比冒泡排序稍微好一点的效能。 // 两两互换 void swap (int* a, int i, …

VSCode 多开、环境对比

前些天发现了一个巨牛的人工智能学习网站&#xff0c;通俗易懂&#xff0c;风趣幽默&#xff0c;忍不住分享一下给大家。点击跳转到教程。 多开&#xff1a; 第一种&#xff1a;win10的开始菜单&#xff0c;在vscode图标右键选择“新开窗口”&#xff0c;这样就多了一个vscode…

前言_工作两年自我感触

17年大学毕业&#xff0c;到今天整整工作两年&#xff0c;从前端到数据分析&#xff0c;从上家公司&#xff08;简称A&#xff09;到现公司&#xff0c;想趁着今天是参加工作两年的纪念日&#xff0c;回忆过往&#xff0c;结合现状有感而发。 刚毕业的时候&#xff0c;啥都学&a…