CArray不包含查找类的函数,使用不便。考虑扩展CArray类,增加Contain函数,通过回调函数暴露数组元素的比较方法,由外部定义。该方法相对重载数组元素的“==”符号更加灵活,可以根据需要配置不同的回调函数进行比较
//类型定义
template<class TYPE, class ARG_TYPE = const TYPE&>
class CArrayEx : public CArray<TYPE,ARG_TYPE>
{
public:
typedef BOOL (CALLBACK *ContainCallBack)(TYPE& T1,TYPE& T2) ; //定义带回调的函数指针,返回类型为BOOL
typedef ContainCallBack FunContainCallBack;
BOOL Contain(FunContainCallBack func,TYPE& T1)
{
BOOL bRes = FALSE;
for (int i=0;i<this->GetSize();i++)
{
TYPE item = this->GetAt(i);
if (TRUE == (bRes = func(item,T1))) break;
}
return bRes;
}
};
//---------------测试用类
typedef struct struTestItem
{
int v1,v2;
struTestItem(){};
struTestItem(const struTestItem& src){CpyData(src);}
struTestItem& struTestItem::operator = (const struTestItem& src) { if(this == &src)return *this;CpyData(src);return *this; }
void CpyData(const struTestItem& src)
{
v1 = src.v1;
v2 = src.v2;
}
bool operator==(const struTestItem& other)const
{
return v1 == other.v1; //默认的比较方法,比较v1
}
} TestItem;
typedef CArrayEx<TestItem,TestItem&> ArrayTestItem;
//定义比较函数,专类专用!!!
//--------------定义2个比较方法,采用不同的逻辑-------
template<class TYPE>
BOOL CALLBACK MyContainsFunc_UseDefault(TYPE& v,TYPE& v2)
{
return v == v2;
}
template<class TYPE>
BOOL CALLBACK MyContainsFunc_ByUseV2(TYPE& v,TYPE& v2) //使用v2作为比较方法
{
//读取成员变量的方法要根据传入的数据类型修改,不能照搬!!
TestItem *pV1 = (TestItem*)&v;
TestItem *pV2 = (TestItem*)&v2;
return pV1->v2 == pV2->v2;
}
测试代码
ArrayTestItem arrTst;
TestItem it1,it2,it3;
it1.v1=1;
it1.v2=2;
it2.v1=3;
it2.v2=4;
it3.v1=5;
it3.v2=2;
arrTst.Add(it1);
arrTst.Add(it2);
//使用MyContainsFunc_UseDefault比较
_tprintf(_T("it1 exists %d\n"),arrTst.Contain(MyContainsFunc_UseDefault,it1));
_tprintf(_T("it3 exists %d\n"),arrTst.Contain(MyContainsFunc_UseDefault,it3));
//使用MyContainsFunc_ByUseV2比较
_tprintf(_T("it3 exists %d\n"),arrTst.Contain(MyContainsFunc_ByUseV2,it3));
输出结果如下: