由于本人要与舍友开发一个codeblock的vim插件,在我们的架构体系中,我们觉得用函数对象池要灵活且易于扩张的多,所以边写了个函数对象池,来管理应用程序中的功能性函数.这个函数对象池可一将一个函数,或者一个成员函数,转换为一个函数对象(Delegate)然后在存入池中,当池满的时候就会进行池的扩张的一些列的动作,大概行为和STL里面的内存池差不多.
一下是实现代码:
//MyEvent.h
#ifndef MYEVENT_H_INCLUDED
#define MYEVENT_H_INCLUDED
#include <vector>
#include <list>
#include <iostream>
#include <typeinfo>
#include <iterator>
using namespace std;
namespace Zsh{
//用于判断对象池中是否已经有了类型和t一样的对象
template <typename T>
int ifind(vector<T> vec,int n,T t){
for(int i = 0;i<n;++i){
if(vec[i] == t)
return i;
}
return -1;
}
//用于查找对象池中可以使用的id号
template <typename T>
int mfind(list<T> v,const T& t){
typename list<T>::iterator ite = v.begin();
for(int i = 0;ite!=v.end();++ite,++i){
if(*ite == t){
return i;
}
}
return -1;
}
//主要用于实现Gelegate的第三个参数,如果传的使对象,那么该对象就要继承这个对象
class ArgObject{
};
//一个代理,相当于时间处理中的EventHandler
template<typename ReturnType,typename ArgsType,typename ObjectType = ArgObject>
class Delegate
{
typedef enum {Object,Function} VarType;//是否用对象初始化的
typedef ReturnType(*ObFunction)(void* ob,ArgsType);//相当不容易啊,用于解决对象成员指针的问题
public:
//以对象来初始化
template <typename RealObjectType>
Delegate(RealObjectType* _object,ReturnType(RealObjectType::*_function)(ArgsType))
:varType(Object),avail(true)
{
of = (ObFunction)(void*)_function;
myArg/*.oper*/.object = _object;
// myArg.oper.ofunction = _function;
}
//以一个函数来初始化
Delegate(ReturnType(*_function)(ArgsType))
:varType(Function),avail(true)
{
myArg.function = _function;
}
Delegate(){}
//函数操作符
ReturnType operator()(ArgsType args){
if(varType == Object)
{
return of(myArg/*.oper*/.object,args);
//return (myArg.oper.object->*(myArg.oper.ofunction))(args);
}else{
return (myArg.function)(args);
}
}
//用于判断两个Delegate是否相等,为了便于运用于标准库中
bool operator==(const Delegate& delegate) const{
bool result;
if(delegate.varType == this->varType){
if(this->varType == Object){
if((typeid(delegate.myArg/*.oper*/.object) == typeid(this->myArg/*.oper*/.object))&&
(this->/*myArg.oper.*/of/*unction*/ == delegate./*myArg.oper*/of/*unction*/)){
result = true;
}else{
result = false;
}
}else{
if(this->myArg.function == delegate.myArg.function){
result = true;
}else{
result = false;
}
}
}else{
result = false;
}
return result;
}
public:
void Enable(){
avail = true;
}
void Disable(){
avail = false;
}
bool isEnable(){
return avail;
}
private:
//定义自己的数据类型
//参数的联合体
union OperArg{
// struct Oper{
// ObjectType* object;
// ReturnType(ObjectType::*ofunction)(ArgsType);
// };
// Oper oper;
ObjectType* object;
ReturnType(*function)(ArgsType);
};
//类的私有成员定义
private:
VarType varType;//实例化参数的类型,是函数指针,还是成员函数指针
OperArg myArg;
ObFunction of;
private:
bool avail;//用于软删除时作标记
};
template<typename ReturnType = void,typename ArgsType = void*>
class OperaTable
{
public:
typedef Delegate<ReturnType,ArgsType> Handler;
typedef vector<Handler> OpTable;
typedef size_t TableId;
public:
OperaTable(const size_t _size):size(_size),opTable(_size){
for(size_t i = 0;i<size;++i)
availableIds.push_back(i);
}
//添加一个Operator对象到池中,返回的是函数对象池中的一个id
TableId addOperator(Handler& handler){
int ite = ifind(opTable,opTable.size(),handler);
if(ite == -1){
//请求新的资源
int id = RequestId();
//将对象放入缓冲池中
if(id != -1){
opTable[id] = handler;
}
--current;
return id;
}else{
//池中已经有了此对象,且可用
if(opTable[ite].isEnable()){
return -1;
}else{
//池中已经有了此对象,但是进行了软删除
opTable[ite].Enable();
--current;
return ite;
}
return -1;
}
}
//从池中删除一个Operator对象
bool deleteOperator(TableId id){
int rid;
if(opTable.size() > id){
//查看id是在使用
rid = mfind(availableIds,id);
//已经在使用
if(rid == -1){
// cout<<"delete object"<<endl;
availableIds.push_back(id);
opTable[id].Disable();
++current;
return true;
//无人使用
}else{
return false;
}
}else{
return false;
}
}
//重载了函数操作符
ReturnType operator()(TableId id,ArgsType args){
return opTable[id].operator()(args);
}
//返回池的大小
size_t Size() const throw(){
return size;
}
//返回池现在用了多少个资源
size_t userdSize() const throw(){
return current;
}
private:
TableId RequestId(){
TableId id = -1;
// 池中已经没有了可用的资源了
if(availableIds.empty()){
ReSize();
}
//返回资源Id
id = availableIds.front();
//资源号为Id的资源不可用了
availableIds.pop_front();
return id;
}
void ReSize(){
availableIds.resize(size<<1);
for(size_t i = size ; i< size<< 1 ; ++i){
availableIds.push_back(i);
}
opTable.resize(size<<1);
size = size<<1;
}
//for test 打印池中的可用资源号用于测试
public:
void printAvailableId(){
copy(availableIds.begin(),availableIds.end(),ostream_iterator<int>(cout," "));
}
private:
size_t size;//记录池的大小
size_t current;//记录池已经使用的资源
OpTable opTable;
list<TableId> availableIds;
};
}
#endif // MYEVENT_H_INCLUDED
//main.cpp
#include <iostream>
#include "MyEvent.h"
using namespace std;
using namespace Zsh;
int function(int){
cout<<"hello world"<<endl;
return 0;
}
class test:public ArgObject{//如果传的成员函数指针,着这个类就必需继承ArgObject
public:
int say(int){
cout<<"hello zsh"<<endl;
a = 1;
b = a<<1;
cout << b<<endl;
if(b == 2){
tmp = "hello jiang li";
cout<<tmp<<endl;
}
return 0;
}
int a;
int b;
string tmp;
};
typedef void (*func_type)(void * obj, int num);
int main()
{
test t;
// int (test::*a)(int) = &test::say;
// void *p = (void*)a;
// int (*p1)(int) = ((int (*)(int))p);
// func_type pa = (func_type)p1;//&test::say;
// pa(&t,1);
OperaTable<int,int> table(10);
Delegate<int,int> opera(function);
Delegate<int,int> opera2(&t,&test::say);
int id = table.addOperator(opera);
table.printAvailableId();
cout<<endl;
int id2 = table.addOperator(opera2);
table.printAvailableId();
cout<<endl;
table(id,1);
table(id2,1);
table.deleteOperator(id2);
table.printAvailableId();
return 0;
}