#include <stdlib.h>
#include <string.h>
#include <stdio.h>
#define CHILD_NUM 4
typedef int Datatype; // 节点数据类型
typedef struct QuadTree* ChildType; // 指向孩子节点指针
int max_leaf_num = 1; // 最大叶节点个数
static int N = 0; // 对叶节点计数的全局变量
// 四叉树节点结构
struct QuadTree
{
Datatype data; // 数据
ChildType child[CHILD_NUM]; // 存放指向四个子树的指针数组
};
// 判断是否为叶节点,是返回1,不是返回0
int isLeaf( QuadTree* node )
{
int i;
for ( i = 0; i < CHILD_NUM; ++i )
{
if ( node->child[i] != NULL ) // 如果存在子树,则不是叶节点
return 0;
}
return 1;
}
// 将长度为n的数组空间扩大两倍
void expandArr( Datatype** out )
{
int n = max_leaf_num;
Datatype* tmpArr = (Datatype*)malloc( sizeof(Datatype) * n);
memcpy( tmpArr, *out, sizeof(Datatype) * n);
free(*out);
*out = (Datatype*)malloc( sizeof(Datatype) * n * 2);
memcpy( *out, tmpArr, sizeof(Datatype) * n );
free( tmpArr );
max_leaf_num = n * 2;
}
// 遍历四叉树,将叶节点数据存储到out所指的数组中
void __travels( QuadTree* root, Datatype** out )
{
int i;
if ( root == NULL )
return;
if ( isLeaf( root ) )
{
if ( N >= max_leaf_num ) // 如果数组空间不足
{
expandArr( out ); // 将数组空间扩大两倍
}
(*out)[N++] = root->data;
return;
}
for ( i = 0; i < CHILD_NUM; ++i )
__travels( root->child[i], out );
}
// 遍历,返回叶节点数目
int Travels( QuadTree* root, Datatype** out )
{
N = 0; // 全局变量,记录也节点个数
__travels( root, out );
return N;
}
// 初始化
QuadTree* InitTree()
{
int i;
QuadTree* root = (QuadTree*)malloc(sizeof(QuadTree));
for ( i = 0; i < CHILD_NUM; ++i )
{
root->child[i] = NULL;
}
return root;
}
// 释放树空间
void ReleaseTree( QuadTree** root )
{
int i;
QuadTree* node = *root;
if ( node == NULL )
return;
else
{
for ( i = 0; i < CHILD_NUM; ++i )
{
ReleaseTree( &(node->child[i]) );
}
free( node );
}
*root = NULL;
}
// 在root的第n个孩子处插入数据d
void InsertData( QuadTree* root, Datatype d, int n )
{
int i;
QuadTree* tmpNode = NULL;
if ( n < 0 || n >= 4 || root == NULL ) // 如果n不为0,1,2,3或者root为空,这直接结束
return;
if ( root->child[n] != NULL ) // 如果root的第n个孩子节点已经有数据,则用d替换该数据
root->child[n]->data = d;
else // 否则,分配一个新节点,该节点数据为d,让child[n]指向该节点
{
tmpNode = (QuadTree*)malloc(sizeof(QuadTree));
for ( i = 0; i < CHILD_NUM; ++i )
{
tmpNode->child[i] = NULL;
}
tmpNode->data = d;
root->child[n] = tmpNode;
}
}
int main()
{
int i;
QuadTree* root = InitTree();
root->data = 10;
for ( i = 0; i < CHILD_NUM-1; ++i )
{
InsertData( root, i*i, i);
}
for ( i = 0; i < CHILD_NUM; ++i )
{
InsertData( root->child[0], root->data + i+2, i);
}
Datatype* leafData = (Datatype*)malloc( sizeof(Datatype) * max_leaf_num );
int K = Travels( root, &leafData );
for ( int i = 0; i < K; ++i )
{
printf("%d\n", leafData[i] );
}
ReleaseTree( &root );
return 0;
}
四叉树递归遍历叶节点并输出至数组
最新推荐文章于 2023-12-02 08:00:00 发布