假设我们有两个类:
class Base
{
private:
int x;
public:
void f();
};
class Foo
{
// some variables and methods
};
现在每个人都可以致电Base::f()
,但我只希望Foo
能够这样做。
为了达到此效果,我们可以将Base::f()
设为私有,并将Foo
声明为朋友:
class Base
{
private:
int x;
void f();
friend Foo;
};
此方法存在的问题是Foo
可以访问Base::f()
和Base::x
(甚至可以访问Base
的任何其他私有成员)。但我希望Foo
只能访问Base::f()
。
类(或函数)是否有办法仅授予对另一个类的某些私有成员的访问权限?或者也许任何人都可以建议更好地解决我的问题?
修改
我会尝试指定我需要的访问限制。首先,Base
是库中的接口(事实上它是一个抽象类)。用户仅使用从Base
派生的类。 Base::f()
仅由Foo
调用,Base::f()
是库中的另一个类。隐藏用户Foo
非常重要,因为只有Foo
知道何时调用它。与此同时,Base
不应该弄乱{{1}}的其他成员。
答案 0 :(得分:6)
非常hacky,但这将允许非常精细的访问。
class Base
{
private:
int x;
void f();
friend class Base_f_Accessor;
};
class Base_f_Accessor
{
private:
static void f(Base & b) { b.f(); }
friend class Foo;
}
class Foo
{
// some variables and methods
};
答案 1 :(得分:4)
您可以创建另一个包含Base
数据的类,如下所示:
class BaseData {
protected:
int x;
};
class Base : public BaseData {
friend class Foo;
void f ();
};
现在,Foo
可以像f
那样访问Base
,但不能访问x
。友谊不是可交换的。使用protected
时,x
对所有人都是私密的,除了那些直接来自BaseData
的人。
更好的方法可能是使用多重继承来定义Base
,并且只对Foo
派生的那些类提供Base
访问权限。
class With_f {
friend class Foo;
protected:
virtual void f () = 0;
};
class With_g {
protected:
virtual void g () = 0;
};
class Base : public With_f, public With_g {
int x;
void f () {}
void g () {}
};
此处,Foo
必须有With_f
指向Base
的指针,但它可以访问f
方法。 Foo
无法访问g
。
答案 2 :(得分:2)
实现这一目标并非易事,非黑客的方法。 C ++根本就没有这种访问控制粒度。您可以使用一些继承,但增加的复杂性超过了此访问限制可能具有的任何优势。此外,此方法无法扩展 - 您只能将增加的权限授予一个朋友类。
答案 3 :(得分:0)
也许有点麻烦,但是您可以创建嵌套类,其中嵌套类是朋友,然后您可以为每个嵌套类添加朋友。这提供了一定程度的粒度:
#include <iostream>
class Nesting
{
friend class Foo;
class Nested1
{
friend class Nesting;
public:
Nested1() : i(3) { }
private:
int i;
} n1;
class Nested2
{
friend class Nesting;
friend class Foo;
public:
Nested2() : j(5) { }
private:
int j;
} n2;
int f() { return n1.i; }
};
class Foo
{
public:
Foo(Nesting& n1) : n(n1) { }
int getJ() { return n.n2.j + n.f(); }
private:
Nesting& n;
};
int main()
{
Nesting n;
Foo foo(n);
std::cout << foo.getJ() << "\n";
}