added LifetimeCallback.h
This commit is contained in:
37
inc/hgl/type/LifetimeCallback.h
Normal file
37
inc/hgl/type/LifetimeCallback.h
Normal file
@@ -0,0 +1,37 @@
|
||||
#pragma once
|
||||
|
||||
#include<hgl/TypeFunc.h>
|
||||
namespace hgl
|
||||
{
|
||||
/**
|
||||
* ԭ<><D4AD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ڴ<EFBFBD><DAB4><EFBFBD><EFBFBD>ص<EFBFBD>
|
||||
*/
|
||||
template<typename T> struct RawLifetimeCallback
|
||||
{
|
||||
virtual bool Create(T *){return true;}
|
||||
virtual void Clear(T *){return;}
|
||||
|
||||
virtual void Copy(T *dst,T *src,int count)
|
||||
{
|
||||
hgl_cpy(dst,src,count);
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* <20><><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ڴ<EFBFBD><DAB4><EFBFBD><EFBFBD>ص<EFBFBD>
|
||||
*/
|
||||
template<typename T> struct ObjectLifetimeCallback:public RawLifetimeCallback<T *>
|
||||
{
|
||||
virtual bool Create(T **) override=0;
|
||||
virtual void Clear(T **) override=0;
|
||||
};//struct ObjectLifetimeCallback
|
||||
|
||||
/**
|
||||
* ȱʡ<C8B1><CAA1><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD><EFBFBD>ڴ<EFBFBD><DAB4><EFBFBD><EFBFBD>ص<EFBFBD>
|
||||
*/
|
||||
template<typename T> struct DefaultObjectLifetimeCallback:public ObjectLifetimeCallback<T>
|
||||
{
|
||||
virtual bool Create(T **obj) override {*obj=new T;return(true);}
|
||||
virtual void Clear(T **obj) override {if(obj&&*obj)delete *obj;}
|
||||
};//struct DefaultObjectLifetimeCallback
|
||||
}//namespace hgl
|
@@ -11,7 +11,10 @@ namespace hgl
|
||||
if(num<=0)return;
|
||||
|
||||
for(int i=0;i<num;i++)
|
||||
Inactive.Push(Create());
|
||||
{
|
||||
T value=Create();
|
||||
Inactive.Push(value);
|
||||
}
|
||||
|
||||
alloc_count+=num;
|
||||
if(alloc_count>history_max)
|
||||
@@ -160,14 +163,14 @@ namespace hgl
|
||||
|
||||
Clear(p,ic);
|
||||
|
||||
Inactive.ClearData();
|
||||
Inactive.Clear();
|
||||
}
|
||||
|
||||
template<typename T>
|
||||
void Pool<T>::ClearAll()
|
||||
{
|
||||
Clear(Inactive.GetData(),Inactive.GetCount());
|
||||
Inactive.ClearData();
|
||||
Inactive.Clear();
|
||||
|
||||
Clear(Active.GetData(),Active.GetCount());
|
||||
Active.ClearData();
|
||||
|
@@ -1,265 +0,0 @@
|
||||
#ifndef HGL_QUEUE_CPP
|
||||
#define HGL_QUEUE_CPP
|
||||
|
||||
namespace hgl
|
||||
{
|
||||
/**
|
||||
* 本类构造函数
|
||||
* @param m 如果m的值不为0,则表示使用固定的队列大小。固定大小的队列会在一开始即分配好内存。
|
||||
*/
|
||||
template<typename T>
|
||||
Queue<T>::Queue(int m)
|
||||
{
|
||||
cur_count=0;
|
||||
|
||||
if(m)
|
||||
{
|
||||
max_count=m;
|
||||
|
||||
items=hgl_align_malloc<T>(max_count);
|
||||
}
|
||||
else max_count=0;
|
||||
|
||||
alloc_count=max_count;
|
||||
}
|
||||
|
||||
template<typename T>
|
||||
Queue<T>::~Queue()
|
||||
{
|
||||
if(cur_count||max_count)hgl_free(items);
|
||||
}
|
||||
|
||||
template<typename T>
|
||||
bool Queue<T>::AllocMemory(int count)
|
||||
{
|
||||
if(max_count)
|
||||
if(count>max_count)return(false);
|
||||
|
||||
if(cur_count)
|
||||
{
|
||||
if(count>alloc_count)
|
||||
{
|
||||
alloc_count=power_to_2(count);
|
||||
|
||||
items=(T *)hgl_align_realloc<T>(items,alloc_count);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
alloc_count=power_to_2(count);
|
||||
|
||||
items=hgl_align_malloc<T>(alloc_count);
|
||||
}
|
||||
|
||||
return(true);
|
||||
}
|
||||
|
||||
/**
|
||||
* 修改队列的最大值
|
||||
*/
|
||||
template<typename T>
|
||||
bool Queue<T>::SetMaxCount(int m)
|
||||
{
|
||||
if(max_count)
|
||||
{
|
||||
if(max_count==m)return(true);
|
||||
}
|
||||
|
||||
if(cur_count)
|
||||
{
|
||||
if(cur_count>m)
|
||||
return(false);
|
||||
}
|
||||
|
||||
max_count=m;
|
||||
return(true);
|
||||
}
|
||||
|
||||
/**
|
||||
* 清除队列中的所有数据
|
||||
*/
|
||||
template<typename T>
|
||||
void Queue<T>::Free()
|
||||
{
|
||||
if(max_count==0)
|
||||
if(cur_count)
|
||||
{
|
||||
hgl_free(items);
|
||||
alloc_count=0;
|
||||
}
|
||||
|
||||
cur_count=0;
|
||||
}
|
||||
|
||||
/**
|
||||
* 清除队列中的所有数据,但不释放内存
|
||||
*/
|
||||
template<typename T>
|
||||
void Queue<T>::ClearData()
|
||||
{
|
||||
cur_count=0;
|
||||
}
|
||||
|
||||
/**
|
||||
* 访问队列中的一个数据,但不清除它
|
||||
* @param t 取出的数据保存地
|
||||
* @return 是否成功取出数据
|
||||
*/
|
||||
template<typename T>
|
||||
bool Queue<T>::Peek(T &t)
|
||||
{
|
||||
if(cur_count)
|
||||
{
|
||||
// t=items[0];
|
||||
memcpy(&t,items,sizeof(T));
|
||||
return(true);
|
||||
}
|
||||
else
|
||||
return(false);
|
||||
}
|
||||
|
||||
/**
|
||||
* 删除队列中的指定数据
|
||||
* @param index 索引
|
||||
*/
|
||||
template<typename T>
|
||||
bool Queue<T>::Delete(int index)
|
||||
{
|
||||
if(index<0||index>=cur_count)
|
||||
return(false);
|
||||
|
||||
cur_count--;
|
||||
|
||||
if(cur_count)
|
||||
{
|
||||
if(index<cur_count)
|
||||
memmove(items+index,items+index+1,(cur_count-index)*sizeof(T));
|
||||
}
|
||||
|
||||
return(true);
|
||||
}
|
||||
|
||||
/**
|
||||
* 从队列中取出一个数据
|
||||
* @param t 取出的数据保存地
|
||||
* @return 是否成功取出数据
|
||||
*/
|
||||
template<typename T>
|
||||
bool Queue<T>::Pop(T &t)
|
||||
{
|
||||
if(cur_count)
|
||||
{
|
||||
// t=items[0];
|
||||
memcpy(&t,items,sizeof(T));
|
||||
|
||||
cur_count--;
|
||||
|
||||
if(max_count==0)
|
||||
{
|
||||
if(cur_count)
|
||||
{
|
||||
//memcpy(items,items+1,count*sizeof(T));
|
||||
memmove(items,items+1,cur_count*sizeof(T));
|
||||
// items=(T *)hgl_realloc(items,count*sizeof(T));
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
memcpy(items,items+1,cur_count*sizeof(T));
|
||||
}
|
||||
|
||||
return(true);
|
||||
}
|
||||
else
|
||||
return(false);
|
||||
}
|
||||
|
||||
/**
|
||||
* 向队列中放入一个数据
|
||||
* @param data 要放入的数据指针
|
||||
* @return true 放入数据成功
|
||||
* @return false 放入数据失败
|
||||
*/
|
||||
template<typename T>
|
||||
bool Queue<T>::Push(const T &data)
|
||||
{
|
||||
if(!AllocMemory(cur_count+1))
|
||||
return(false);
|
||||
|
||||
// items[count++]=data;
|
||||
memcpy(items+cur_count,&data,sizeof(T));
|
||||
cur_count++;
|
||||
|
||||
return(true);
|
||||
}
|
||||
|
||||
/**
|
||||
* 向队列中压入一堆数据
|
||||
* @param dp 要放入的数据指针
|
||||
* @param dc 要放入的数据数量
|
||||
*/
|
||||
template<typename T>
|
||||
bool Queue<T>::Push(T *dp,const int dc)
|
||||
{
|
||||
if(!AllocMemory(cur_count+dc))
|
||||
return(false);
|
||||
|
||||
memcpy(items+cur_count,dp,sizeof(T)*dc);
|
||||
cur_count+=dc;
|
||||
|
||||
return(true);
|
||||
}
|
||||
|
||||
template<typename T>
|
||||
int Queue<T>::Find(const T &data)
|
||||
{
|
||||
if(cur_count<=0)
|
||||
return(-1);
|
||||
|
||||
T *p=items;
|
||||
for(int i=0;i<cur_count;i++)
|
||||
{
|
||||
if(*p==data)
|
||||
return(i);
|
||||
|
||||
++p;
|
||||
}
|
||||
|
||||
return(-1);
|
||||
}
|
||||
|
||||
template<typename T>
|
||||
void Queue<T>::operator =(const Queue<T> &ori)
|
||||
{
|
||||
if(ori.cur_count==0)return;
|
||||
|
||||
Free();
|
||||
|
||||
max_count=ori.cur_count;
|
||||
cur_count=ori.cur_count;
|
||||
|
||||
if(max_count==0)
|
||||
alloc_count=cur_count;
|
||||
else
|
||||
alloc_count=max_count;
|
||||
|
||||
items=hgl_align_malloc<T>(alloc_count);
|
||||
|
||||
memcpy(items,ori.items,alloc_count*sizeof(T));
|
||||
}
|
||||
}
|
||||
|
||||
namespace hgl
|
||||
{
|
||||
template<typename T>
|
||||
void QueueObject<T>::Clear()
|
||||
{
|
||||
int n=Queue<T *>::cur_count;
|
||||
|
||||
while(n--)
|
||||
delete Queue<T *>::items[n];
|
||||
|
||||
Queue<T *>::Free();
|
||||
}
|
||||
}
|
||||
#endif//HGL_QUEUE_CPP
|
@@ -1,82 +1,180 @@
|
||||
#ifndef HGL_QUEUE_INCLUDE
|
||||
#define HGL_QUEUE_INCLUDE
|
||||
#pragma once
|
||||
|
||||
#include<hgl/type/DataType.h>
|
||||
#include<hgl/type/DataArray.h>
|
||||
namespace hgl
|
||||
{
|
||||
/**
|
||||
* Queue模板类用于保存一个先进先出、后进后出的数据队列
|
||||
*
|
||||
* 注:这个类还在测试中,请不要修改这个类的源代码,如有修改意见,请致电作者。
|
||||
*/
|
||||
template<typename T> class Queue ///队列顺序数据访问类
|
||||
{
|
||||
protected:
|
||||
|
||||
int max_count; ///<最大可分配空间数量
|
||||
int alloc_count; ///<已分配的空间数量
|
||||
int cur_count;
|
||||
T *items;
|
||||
DataArray<T> data_array[2];
|
||||
|
||||
int read_index;
|
||||
int write_index;
|
||||
|
||||
int read_offset;
|
||||
|
||||
protected:
|
||||
|
||||
bool AllocMemory(int);
|
||||
void SwapIndex()
|
||||
{
|
||||
if(read_index==0)
|
||||
{
|
||||
read_index=1;
|
||||
write_index=0;
|
||||
}
|
||||
else
|
||||
{
|
||||
read_index=0;
|
||||
write_index=1;
|
||||
}
|
||||
|
||||
read_offset=0;
|
||||
}
|
||||
|
||||
public: //属性
|
||||
|
||||
T * GetData ()const{return items;} ///<取得原始数据
|
||||
int GetCount ()const{return cur_count;} ///<取得数据数量
|
||||
const int GetAllocCount ()const{return data_array[0].GetAllocCount()+
|
||||
data_array[1].GetAllocCount();} ///<取得已分配的数据数量
|
||||
|
||||
int GetMaxCount ()const{return max_count;} ///<取得最大数量
|
||||
bool SetMaxCount (int); ///<设置最大数量
|
||||
const int GetCount ()const{return data_array[0].GetCount()+
|
||||
data_array[1].GetCount();} ///<取得列表内数据数量
|
||||
|
||||
const T *begin()const{return items;}
|
||||
const T *end()const{return items+cur_count;}
|
||||
virtual bool PreAlloc (int count) ///<预分配数据空间
|
||||
{
|
||||
if(!data_array[0].Alloc(count))return(false);
|
||||
if(!data_array[1].Alloc(count))return(false);
|
||||
|
||||
return(true);
|
||||
}
|
||||
|
||||
const bool IsEmpty ()const{return GetCount()==0;} ///<确认列表是否为空
|
||||
|
||||
public: //方法
|
||||
|
||||
Queue(int=0);
|
||||
virtual ~Queue();
|
||||
|
||||
bool Peek (T &); ///<尝试访问一个数据
|
||||
bool Pop (T &); ///<弹出一个数据
|
||||
bool Push (const T &); ///<压入一个数据
|
||||
bool Push (T *,int); ///<压入一批数据
|
||||
|
||||
int Find (const T &); ///<查找队列中这个数据的编号
|
||||
bool IsExist (const T &data)const{return this->Find(data)!=-1;} ///<确认是否有这个数据
|
||||
bool Delete (int); ///<删除队列中指定编号的数据
|
||||
|
||||
void Free (); ///<清除所有数据
|
||||
void ClearData (); ///<清除所有数据,但不释放内存
|
||||
|
||||
bool GetItem (int n,T &ti) ///<取得指定项数据
|
||||
Queue()
|
||||
{
|
||||
if(n<0||n>=cur_count)return(false);
|
||||
write_index=0;
|
||||
read_index=1;
|
||||
read_offset=0;
|
||||
}
|
||||
|
||||
virtual ~Queue()=default;
|
||||
|
||||
virtual bool Push (T *data,int count) ///<压入一批数据
|
||||
{
|
||||
if(!data||count<=0)return(false);
|
||||
|
||||
int offset=data_array[write_index].GetCount();
|
||||
|
||||
if(!data_array[write_index].AddCount(count))
|
||||
return(false);
|
||||
|
||||
data_array[write_index].WriteAt(data,offset,count);
|
||||
|
||||
ti=items[n];
|
||||
return(true);
|
||||
}
|
||||
|
||||
virtual void operator =(const Queue<T> &);
|
||||
virtual bool Push (T &data){return Push(&data,1);} ///<压入一个数据
|
||||
|
||||
virtual bool Peek (T &data) ///<尝试访问一个数据
|
||||
{
|
||||
if(data_array[read_index].GetCount()>=read_offset)
|
||||
{
|
||||
if(data_array[write_index].GetCount()<=0)
|
||||
return(false);
|
||||
|
||||
data_array[write_index].ReadAt(data,0);
|
||||
|
||||
}
|
||||
else
|
||||
{
|
||||
data_array[read_index].ReadAt(data,read_offset);
|
||||
}
|
||||
|
||||
return(true);
|
||||
}
|
||||
|
||||
virtual bool Pop (T &data) ///<弹出一个数据
|
||||
{
|
||||
if(data_array[read_index].GetCount()>=read_offset)
|
||||
{
|
||||
if(data_array[write_index].GetCount()<=0)
|
||||
return(false);
|
||||
|
||||
data_array[read_index].Clear();
|
||||
|
||||
SwapIndex();
|
||||
|
||||
data_array[read_index].ReadAt(data,0);
|
||||
|
||||
++read_offset;
|
||||
}
|
||||
else
|
||||
{
|
||||
data_array[read_index].ReadAt(data,read_offset);
|
||||
|
||||
++read_offset;
|
||||
}
|
||||
|
||||
return(true);
|
||||
}
|
||||
|
||||
public:
|
||||
|
||||
virtual void Clear (){data_array[0].Clear();data_array[1].Clear();} ///<清除所有数据
|
||||
virtual void Free (){data_array[0].Free();data_array[1].Free();} ///<清除所有数据并释放内存
|
||||
};//template<typename T> class Queue
|
||||
|
||||
template<typename T> class QueueObject:public Queue<T *> ///堆栈对象
|
||||
template<typename T> class ObjectQueue:public Queue<T *> ///对象队列
|
||||
{
|
||||
protected:
|
||||
|
||||
virtual void DeleteObject(T *obj){if(obj)delete obj;}
|
||||
|
||||
public:
|
||||
|
||||
using Queue<T *>::Queue;
|
||||
virtual ~QueueObject(){Clear();}
|
||||
virtual ~ObjectQueue(){Free();}
|
||||
|
||||
void Clear();
|
||||
|
||||
T *operator[](int n)const
|
||||
virtual bool Push(T *obj)
|
||||
{
|
||||
if(n<0||n>=Queue<T *>::cur_count)return(nullptr);
|
||||
if(!obj)return(false);
|
||||
|
||||
return Queue<T *>::items[n];
|
||||
return Queue<T *>::Push(obj);
|
||||
}
|
||||
};//template<typename T> class QueueObject
|
||||
|
||||
virtual T *Pop()
|
||||
{
|
||||
T *obj;
|
||||
|
||||
if(!Queue<T *>::Pop(obj))
|
||||
return(nullptr);
|
||||
|
||||
return obj;
|
||||
}
|
||||
|
||||
void Clear()
|
||||
{
|
||||
for(T *obj:data_array[0])
|
||||
DeleteObject(obj);
|
||||
|
||||
for(T *obj:data_array[1])
|
||||
DeleteObject(obj);
|
||||
|
||||
data_array[0].Clear();
|
||||
data_array[1].Clear();
|
||||
}
|
||||
|
||||
void Free()
|
||||
{
|
||||
ObjectQueue<T>::Clear();
|
||||
|
||||
data_array[0].Free();
|
||||
data_array[1].Free();
|
||||
}
|
||||
};//template<typename T> class ObjectQueue
|
||||
}//namespace hgl
|
||||
#include<hgl/type/Queue.cpp>
|
||||
#endif//HGL_QUEUE_INCLUDE
|
||||
|
@@ -5,8 +5,6 @@ namespace hgl
|
||||
{
|
||||
/**
|
||||
* Stack模板类用于保存一个先进后出、后进先出的数据堆栈
|
||||
*
|
||||
* 注:这个类还在测试中,请不要修改这个类的源代码,如有修改意见,请致电作者。
|
||||
*/
|
||||
template<typename T> class Stack ///堆栈顺序数据访问类
|
||||
{
|
||||
@@ -75,8 +73,10 @@ namespace hgl
|
||||
return(true);
|
||||
}
|
||||
|
||||
virtual void Clear(){data_array.Clear();} ///<清除所有数据
|
||||
virtual void Free(){data_array.Free();} ///<清除所有数据并释放内存
|
||||
public:
|
||||
|
||||
virtual void Clear (){data_array.Clear();} ///<清除所有数据
|
||||
virtual void Free (){data_array.Free();} ///<清除所有数据并释放内存
|
||||
|
||||
virtual void operator =(const DataArray<T> &da) ///<复制一个堆栈
|
||||
{
|
||||
|
Reference in New Issue
Block a user