友谊与传承
Friendship and inheritance
我正在做一个小项目,但有点卡住了,因为我不太明白友谊和继承是如何相互作用的。我将向您展示一些示例代码。
namespace a
{
class Foo
{
public:
Foo(int x) : m_x(x) {}
protected:
friend class b::Derived;
friend class a::Base;
int m_x;
};
class Base
{
public:
Base(Foo foo) : m_foo(foo) {}
protected:
Foo m_foo;
};
}
namespace b
{
class Derived : public a::Base
{
public:
Derived(a::Foo foo)
: Base(foo)
{
m_foo.m_x;
}
};
}
e0265: at line 29: member a::Foo::m_x (declared at line 10) is inaccessible
显然Derived不能访问Foo的protected成员,貌似因为Derived::m_foo是派生成员,所以构造Derived会失败。谁能给我详细解释一下?
Apparently Derived can't access private members of Foo, seemingly
because Derived::m_foo is a derived member, so constructing Derived
will fail.
对不起,这不是朋友明显的误会。
朋友 class 可以 访问任何属性。
您有一个不相关的编码错误...评论显示您在 Base 中缺少初始化(Base::m_foo)。解决这个问题,向 Foo 添加一些数据项,然后 运行 你的演示:
#include <iostream>
using std::cout, std::endl;
class Foo
{
public:
Foo(int x): m_x(x){}
~Foo(){}
int m_z; // add public
protected:
int m_y; // add protected
private: // change to private
friend class Derived;
int m_x;
};
class Base
{
public:
Base() : m_foo(0) // add m_foo Initialization (with 0)
{}
virtual ~Base(){}
protected:
Foo m_foo;
};
class Derived : public Base
{
public:
Derived(Foo foo)
{
foo.m_y = 11;
foo.m_z = 22;
std::cout << foo.m_x << " "
<< foo.m_y << " "
<< foo.m_z << std::endl; //friend class can access
}
};
class T914_t // ctor and dtor compiler provided defaults
{
public:
int operator()(int argc, char* argv[]) { return exec(argc, argv); }
private: // methods
int exec(int , char** )
{
Foo f(99);
Derived d(f);
return 0;
}
}; // class T914_t
int main(int argc, char* argv[]) { return T914_t()(argc, argv); } // call functor
来自 class 的派生 ctor 访问私有、受保护和 public 数据属性的典型输出:
99 11 22
我发现了问题。命名空间 b 和因此派生的 class 对于 Foo 中的友元声明是不可见的。当我转发声明 b 并派生时,一切都按预期工作并且派生可以访问 private/protected 成员。
我正在做一个小项目,但有点卡住了,因为我不太明白友谊和继承是如何相互作用的。我将向您展示一些示例代码。
namespace a
{
class Foo
{
public:
Foo(int x) : m_x(x) {}
protected:
friend class b::Derived;
friend class a::Base;
int m_x;
};
class Base
{
public:
Base(Foo foo) : m_foo(foo) {}
protected:
Foo m_foo;
};
}
namespace b
{
class Derived : public a::Base
{
public:
Derived(a::Foo foo)
: Base(foo)
{
m_foo.m_x;
}
};
}
e0265: at line 29: member a::Foo::m_x (declared at line 10) is inaccessible
显然Derived不能访问Foo的protected成员,貌似因为Derived::m_foo是派生成员,所以构造Derived会失败。谁能给我详细解释一下?
Apparently Derived can't access private members of Foo, seemingly because Derived::m_foo is a derived member, so constructing Derived will fail.
对不起,这不是朋友明显的误会。
朋友 class 可以 访问任何属性。
您有一个不相关的编码错误...评论显示您在 Base 中缺少初始化(Base::m_foo)。解决这个问题,向 Foo 添加一些数据项,然后 运行 你的演示:
#include <iostream>
using std::cout, std::endl;
class Foo
{
public:
Foo(int x): m_x(x){}
~Foo(){}
int m_z; // add public
protected:
int m_y; // add protected
private: // change to private
friend class Derived;
int m_x;
};
class Base
{
public:
Base() : m_foo(0) // add m_foo Initialization (with 0)
{}
virtual ~Base(){}
protected:
Foo m_foo;
};
class Derived : public Base
{
public:
Derived(Foo foo)
{
foo.m_y = 11;
foo.m_z = 22;
std::cout << foo.m_x << " "
<< foo.m_y << " "
<< foo.m_z << std::endl; //friend class can access
}
};
class T914_t // ctor and dtor compiler provided defaults
{
public:
int operator()(int argc, char* argv[]) { return exec(argc, argv); }
private: // methods
int exec(int , char** )
{
Foo f(99);
Derived d(f);
return 0;
}
}; // class T914_t
int main(int argc, char* argv[]) { return T914_t()(argc, argv); } // call functor
来自 class 的派生 ctor 访问私有、受保护和 public 数据属性的典型输出:
99 11 22
我发现了问题。命名空间 b 和因此派生的 class 对于 Foo 中的友元声明是不可见的。当我转发声明 b 并派生时,一切都按预期工作并且派生可以访问 private/protected 成员。