朋友基础功能可以访问子数据

时间:2018-09-09 01:00:17

标签: c++ oop

class Child;

class Base
{
    friend bool friendly(const Base&,const Child&) ;
    private:
        std::string name;
    public:
        Base() {}
};

class Child: public Base
{
    private:
        int number;

    public:
        Child() {}

};



bool friendly(const Base &base, const Child &child ) 
{

    return base.name== child.name;
}

我没有使用其他类型。我实际上是通过Child和Base对象来调用一个函数。

friend(Base(),Child());

我不太明白为什么Child可以访问名称变量。 当访问数字成员变量:{child.number}时,使用友好函数编译器会生成编译错误“私有数据”。为什么我看不到名称变量的错误。 它们是不同类型的!

P.S .:我认为这是非常糟糕的设计。我担心C ++ 11的这种特殊行为。

2 个答案:

答案 0 :(得分:1)

我认为这是可以预期的,因为Tickfriendly类的朋友,因此它可以访问Base个私有成员,包括Base

这里name仍是child.name私有成员Base的引用。但是name是不同的,这只是number的私有,这就是child无法访问的原因。

答案 1 :(得分:1)

我认为您的行为不是特别直观,这是正确的,尤其是因为您通常无法访问基类的私有成员。但这不应该是编译错误,因为这种情况实际上是在C ++ 14 ISO标准中提到的(第11.2.5节,由您自己完成的粗体显示):

  

5)如果可以访问基类,则可以将指向派生类的指针隐式转换为指向该基类的指针   等级(4.10,4.11)。 [注意:X类的成员和朋友可以将X *隐式转换为   指向X的私有或受保护的立即基类的指针。—结束说明]对成员的访问受到影响   通过成员所属的类。该命名类是成员名称所在的类   抬头发现。 [注意:此类可以是显式的,例如,当使用qualified-id时,也可以是隐式的,例如,   使用类成员访问运算符(5.2.5)时(包括添加隐式“ this->”的情况)。   如果同时使用类成员访问运算符和限定ID命名成员(如p-> T :: m),则   命名成员的类是由合格ID(即T)的嵌套名称说明符表示的类。   —尾注] 如果在类N中命名,则成员R在点R处可访问

     

(5.1)—作为N的成员的m是公开的,或者

     

(5.2)-m是N的成员   私有,R出现在N类或

的成员或朋友中      

(5.3)—米   因为N的成员受到保护,而R出现在N的成员或朋友中   N类,或来自N的P类的成员或朋友,其中m   因为P的成员是公开的,私有的或受保护的,或者

     

(5.4)-在那里   存在R可以访问的N的基类B,并且m为   在类B中命名时可在R处访问

,并且此示例遵循上述blub:

class B;
class A {
private:
    int i;
    friend void f(B*);
};
class B : public A { };
void f(B* p) {
    p->i = 1; // OK: B* can be implicitly converted to A*,
              // and f has access to i in A
}

您没有使用指针,但是const引用也可以隐式转换。