1. 使用友元类结合模板元编程思路
- 思路:
- 定义一个模板友元类,这个友元类专门用于访问目标类的非公有成员。由于友元关系的存在,友元类可以访问目标类的非公有成员。同时利用模板元编程的特性,可以对访问进行更细粒度的控制,比如只在特定条件下才允许访问。
- 关键代码示例:
// 定义目标类
class TargetClass {
private:
int privateVariable;
public:
TargetClass(int value) : privateVariable(value) {}
// 模板友元类声明
template <typename T>
friend class Accessor;
};
// 模板友元类定义
template <typename T>
class Accessor {
public:
static int getPrivateVariable(T& target) {
return target.privateVariable;
}
};
- 原理解释:
- 在
TargetClass
中,声明了template <typename T> friend class Accessor;
,这使得Accessor
模板类成为TargetClass
的友元。友元关系赋予了Accessor
类访问TargetClass
非公有成员的权限。
Accessor
模板类中的getPrivateVariable
静态成员函数,通过接受TargetClass
类型的引用,能够访问其privateVariable
成员。由于Accessor
是模板类,还可以通过模板参数进一步定制化访问逻辑,比如根据不同的模板参数执行不同的访问策略,从而实现有限制的访问。
2. 使用CRTP(Curiously Recurring Template Pattern)思路
- 思路:
- 利用CRTP,让目标类继承自一个模板类,在模板类中定义访问目标类非公有成员的接口。这样既不需要修改目标类的非公有成员属性,又能在模板类层次实现对非公有成员的访问。
- 关键代码示例:
// 模板基类
template <typename Derived>
class BaseAccessor {
public:
int getPrivateVariable() {
return static_cast<Derived*>(this)->privateVariable;
}
};
// 目标类继承自模板基类
class TargetClass : public BaseAccessor<TargetClass> {
private:
int privateVariable;
public:
TargetClass(int value) : privateVariable(value) {}
};
- 原理解释:
TargetClass
继承自BaseAccessor<TargetClass>
,利用CRTP的特性,BaseAccessor
中的成员函数可以通过static_cast<Derived*>(this)
将this
指针转换为派生类指针,从而访问派生类(即TargetClass
)的非公有成员privateVariable
。这种方式在不改变TargetClass
非公有成员访问属性的前提下,实现了在BaseAccessor
层次对TargetClass
非公有成员的访问,达到了有限制访问的目的。