增加全新的TreeNode节点

This commit is contained in:
hyzboy 2025-04-27 00:50:59 +08:00
parent 3f92832a6f
commit c50f9eac72
4 changed files with 398 additions and 0 deletions

204
inc/hgl/type/TreeNode.h Normal file
View File

@ -0,0 +1,204 @@
#pragma once
#include<hgl/TypeFunc.h>
#include<typeinfo>
#include<tsl/robin_map.h>
#include<tsl/robin_set.h>
namespace hgl
{
class TreeBaseNodeManager;
template<typename T> class TreeNodeManager;
enum class TreeNodeLifePhase
{
None=0, ///<未知
Work, ///<工作中(一般的使用状态)
Recycled, ///<已回收(走过了回收流程,但并未释放资源)
WaitDestory, ///<等待销毁(已经进入真正的销毁流程)
Destory, ///<销毁(已经被销毁不存这种对像只在根据ID获取状态时可以得到)
ENUM_CLASS_RANGE(None,Destory)
};
class TreeBaseNode
{
TreeBaseNodeManager *manager; ///<管理器指针
size_t unique_id; ///<唯一ID
TreeBaseNode *parent_node; ///<父节点指针
tsl::robin_map<size_t,TreeBaseNode *> child_map; ///<子节点集合
TreeNodeLifePhase life_phase; ///<生命周期状态
public:
TreeBaseNodeManager *GetManager() {return manager;} ///<获取管理器指针
const TreeBaseNodeManager *GetManager()const{return manager;} ///<获取管理器指针
const size_t GetManagerID ()const; ///<获取管理器ID
const size_t GetUniqueID ()const{return unique_id;} ///<获取对象唯一ID
const TreeNodeLifePhase GetLifePhase()const{return life_phase;} ///<获取生命周期状态
const bool IsWork ()const{return life_phase==TreeNodeLifePhase::Work;} ///<可以工作
const bool IsRecycled ()const{return life_phase==TreeNodeLifePhase::Recycled;} ///<是否已经回收
const bool IsWaitDestory()const{return life_phase==TreeNodeLifePhase::WaitDestory;} ///<是否已经进入等待销毁状态
private:
friend class TreeBaseNodeManager;
template<typename T> friend class TreeNode;
template<typename T> friend class TreeNodeManager;
TreeBaseNode(TreeBaseNodeManager *nm,const size_t uid);
virtual ~TreeBaseNode();
protected:
virtual void MarkWaitDestory(){life_phase=TreeNodeLifePhase::WaitDestory;} ///<标记为等待销毁状态
virtual void OnDestory(); ///<最后的真实销毁调用操作(默认为delete this)
public:
virtual void Destory(); ///<销毁节点(标记为等待销毁状态)
public: //子节点相关
virtual void OnAttachParent(TreeBaseNode *pn){parent_node=pn;} ///<被附加到父节点时调用(参见AttachChild)
virtual void OnDetachParent(TreeBaseNode *pn){parent_node=nullptr;} ///<被从父节点中移除时调用(参见DetachChild)
const TreeBaseNode * GetParent()const{return parent_node;} ///<获取父节点指针
const size_t GetChildCount()const{return child_map.size();} ///<获取子节点数量
const bool Contains(const size_t id)const{return child_map.contains(id);} ///<根据ID判断是否包含子节点
const bool Contains(const TreeBaseNode *node)const;
const bool AttachChild(TreeBaseNode *node);
void DetachChild(TreeBaseNode *node);
void DestoryAllChild();
};//class TreeBaseNode
class TreeBaseNodeManager
{
static const size_t AcquireManagerID(){static size_t id_count=0;return ++id_count;}
private:
size_t manager_serial;
size_t node_serial;
private:
tsl::robin_map<size_t,TreeBaseNode *> node_map; ///<节点集合
tsl::robin_set<TreeBaseNode *> wait_destory_node_set; ///<等待销毁的节点集合
tsl::robin_set<TreeBaseNode *> destored_node_set; ///<已经销毁的节点集合
protected:
friend class TreeBaseNode;
const size_t AcquireNodeID(){return ++node_serial;}
virtual TreeBaseNode * OnCreateNode(const size_t node_id)=0; ///<创建节点时调用
virtual void OnDestoryNode(TreeBaseNode *node)=0; ///<销毁节点时调用
void OnNodeDirectDestory(TreeBaseNode *node); ///<直接销毁这种情况只在对象被直接delete的情况下一般不需要
public:
const size_t GetMangaerID()const{return manager_serial;}
public:
TreeBaseNodeManager()
{
manager_serial=AcquireManagerID();
node_serial=0;
}
virtual ~TreeBaseNodeManager(){}
virtual void ForceClear();
TreeBaseNode * CreateNode();
const bool ContainsNode(TreeBaseNode *tn)const;
bool DestoryNode(TreeBaseNode *node);
TreeBaseNode * GetNode(const size_t node_id);
virtual void Update(){}
};//class TreeBaseNodeManager
template<typename T> class TreeNode:public TreeBaseNode
{
T node_data;
private:
friend class TreeNodeManager<T>; ///<树节点管理器
using TreeBaseNode::TreeBaseNode;
public:
virtual ~TreeNode()override{}
public:
operator T &() {return node_data;}
operator const T &()const {return node_data;}
T &operator *() {return node_data;}
const T &operator *()const{return node_data;}
T &get() {return node_data;}
const T &get()const {return node_data;}
T *operator ->() {return &node_data;}
const T *operator ->()const {return &node_data;}
T &operator = (const T &data)
{
node_data=data;
return node_data;
}
};//class TreeNode
template<typename T> class TreeNodeManager:public TreeBaseNodeManager
{
public:
using NodeType=TreeNode<T>; ///<节点类型
protected:
TreeBaseNode *OnCreateNode(const size_t node_id) override
{
return(new NodeType(this,node_id));
}
void OnDestoryNode(TreeBaseNode *node)override
{
if(!node)return;
node->OnDestory();
}
public:
using TreeBaseNodeManager::TreeBaseNodeManager;
virtual ~TreeNodeManager()
{
ForceClear();
}
NodeType *Create(){return (NodeType *)CreateNode();}
};//class TreeNodeManager
}//namespace hgl

View File

@ -42,6 +42,12 @@ SET(TYPE_DATA_CHAIN_SOURCE ${TYPE_INCLUDE_PATH}/DataChain.h
SOURCE_GROUP("DataType\\DataChain" FILES ${TYPE_DATA_CHAIN_SOURCE}) SOURCE_GROUP("DataType\\DataChain" FILES ${TYPE_DATA_CHAIN_SOURCE})
SET(TREE_NODE_FILES ${TYPE_INCLUDE_PATH}/TreeNode.h
Type/TreeNode.cpp
Type/TreeNodeManager.cpp)
SOURCE_GROUP("DataType\\Tree" FILES ${TREE_NODE_FILES})
SET(ACTIVE_MANAGER_FILES ${TYPE_INCLUDE_PATH}/ActiveIDManager.h SET(ACTIVE_MANAGER_FILES ${TYPE_INCLUDE_PATH}/ActiveIDManager.h
${TYPE_INCLUDE_PATH}/ActiveMemoryBlockManager.h ${TYPE_INCLUDE_PATH}/ActiveMemoryBlockManager.h
${TYPE_INCLUDE_PATH}/ActiveDataManager.h ${TYPE_INCLUDE_PATH}/ActiveDataManager.h
@ -52,6 +58,7 @@ file(GLOB TYPE_TEMPLATE_HEADER ${TYPE_INCLUDE_PATH}/*.h)
SOURCE_GROUP("DataType\\ActiveManager" FILES ${ACTIVE_MANAGER_FILES}) SOURCE_GROUP("DataType\\ActiveManager" FILES ${ACTIVE_MANAGER_FILES})
SET(SYSTEM_INFO_SOURCE ${CORE_PLATFORM_INCLUDE_PATH}/SystemInfo.h SET(SYSTEM_INFO_SOURCE ${CORE_PLATFORM_INCLUDE_PATH}/SystemInfo.h
SystemInfo.cpp) SystemInfo.cpp)
@ -261,6 +268,8 @@ add_cm_library(CMCore "CM" ${CORE_PLATFORM_HEADER_FILES}
${BITS_ARRAY_FILES} ${BITS_ARRAY_FILES}
${TREE_NODE_FILES}
${COLOR_HEADER_FILES} ${COLOR_HEADER_FILES}
${COLOR_SOURCE_FILES} ${COLOR_SOURCE_FILES}

93
src/Type/TreeNode.cpp Normal file
View File

@ -0,0 +1,93 @@
#include<hgl/type/TreeNode.h>
namespace hgl
{
TreeBaseNode::TreeBaseNode(TreeBaseNodeManager *nm,const size_t uid)
{
manager=nm;
unique_id=uid;
life_phase=TreeNodeLifePhase::None;
parent_node=nullptr;
}
TreeBaseNode::~TreeBaseNode()
{
if(GetChildCount())
DestoryAllChild();
if(parent_node)
parent_node->DetachChild(this); //从父节点中移除
if(life_phase<TreeNodeLifePhase::WaitDestory) //还没有进入销毁器
manager->OnNodeDirectDestory(this); //直接销毁
}
const size_t TreeBaseNode::GetManagerID()const
{
return manager->GetMangaerID();
}
void TreeBaseNode::Destory()
{
manager->DestoryNode(this);
}
void TreeBaseNode::OnDestory()
{
life_phase=TreeNodeLifePhase::Destory; //设置为销毁状态
delete this;
}
const bool TreeBaseNode::Contains(const TreeBaseNode *node)const
{
if(!node)return(false);
if(node->GetManager()!=GetManager())return(false);
return Contains(node->GetUniqueID());
}
const bool TreeBaseNode::AttachChild(TreeBaseNode *node)
{
if(!node)return(false);
if(Contains(node))return(false);
child_map.emplace(node->GetUniqueID(),node);
node->OnAttachParent(this);
return(true);
}
void TreeBaseNode::DetachChild(TreeBaseNode *node)
{
if(!node)return;
if(node->GetManager()!=GetManager())
return;
const size_t child_id=node->GetUniqueID();
if(child_map.contains(child_id))
child_map.erase(child_id);
node->OnDetachParent(this);
}
void TreeBaseNode::DestoryAllChild()
{
for(auto &it:child_map)
{
TreeBaseNode *node=it.second;
if(!node)
continue;
child_map.erase(node->GetUniqueID()); //从子节点集合中移除
node->OnDetachParent(this); //从父节点中移除
node->Destory(); //销毁子节点
}
child_map.clear();
}
}//namespace hgl

View File

@ -0,0 +1,92 @@
#include<hgl/type/TreeNode.h>
namespace hgl
{
void TreeBaseNodeManager::OnNodeDirectDestory(TreeBaseNode *node) ///<直接销毁这种情况只在对象被直接delete的情况下一般不需要
{
if(!node)return;
if(wait_destory_node_set.contains(node))
wait_destory_node_set.erase(node);
if(!destored_node_set.contains(node))
destored_node_set.emplace(node);
}
void TreeBaseNodeManager::ForceClear()
{
if(!node_map.empty())
{
for(auto &it:node_map)
{
it.second->MarkWaitDestory();
wait_destory_node_set.insert(it.second);
}
node_map.clear();
}
//正式的销毁可能是需要考虑node顺序的需要根据依赖进行排序.这里暂时没做。
if(!wait_destory_node_set.empty())
{
for(auto *node:wait_destory_node_set)
OnDestoryNode(node); //销毁节点
wait_destory_node_set.clear();
}
}
TreeBaseNode *TreeBaseNodeManager::CreateNode()
{
const size_t node_id=AcquireNodeID();
TreeBaseNode *node=OnCreateNode(node_id);
if(!node)
return(nullptr);
node_map.emplace(node_id,node);
return(node);
}
const bool TreeBaseNodeManager::ContainsNode(TreeBaseNode *tn)const
{
if(!tn)return(false);
if(tn->GetManagerID()!=GetMangaerID())return(false);
if(!node_map.contains(tn->GetUniqueID()))
return(false);
return(true);
}
bool TreeBaseNodeManager::DestoryNode(TreeBaseNode *node)
{
if(!node)return(false);
if(wait_destory_node_set.contains(node))
return(true);
if(!ContainsNode(node))
return(false);
node->MarkWaitDestory();
node_map.erase(node->GetUniqueID());
wait_destory_node_set.insert(node);
return(true);
}
TreeBaseNode *TreeBaseNodeManager::GetNode(const size_t node_id)
{
auto iter=node_map.find(node_id);
if(iter==node_map.end())
return(nullptr);
return(iter->second);
}
}//namespace hgl