为什么吸气手和二传手来自不同的"bases"?

Why getter and setter are called from different "bases"?

本文关键字:bases 二传手 为什么      更新时间:2023-10-16

程序的输出是a2a3。 我知道,E类有两个"基本实例",因为从B继承不是虚拟的。 谁能解释为什么从E类B类的一个"基本实例"调用set_c,而get_c类则从另一个"基本实例"调用?

代码来自这里:http://www.interqiew.com/ask?ta=tqcpp04&qn=2

#include <iostream>
class A
{
public:
A(int n = 2) : m_n(n) {}
public:
int get_n() const { return m_n; }
void set_n(int n) { m_n = n; }
private:
int m_n;
};
class B
{
public:
B(char c = 'a') : m_c(c) {}
public:
char get_c() const { return m_c; }
void set_c(char c) { m_c = c; }
private:
char m_c;
};
class C
: virtual public A
, public B
{ };
class D
: virtual public A
, public B
{ };
class E
: public C
, public D
{ };
int main()
{
E e;
C &c = e;
D &d = e;
std::cout << c.get_c() << d.get_n();
c.set_n(3);
d.set_c('b');
std::cout << c.get_c() << d.get_n() << std::endl;
return 0;
}

C++名称查找会考虑正在查找的类的子对象,并将子对象与它找到的名称相关联。这种关联是知道成员函数应该对哪个对象进行操作。找到名称并与一个对象关联(查找是明确的(后,查找将停止。这些规则比我介绍的摘要要复杂得多,但我们已经可以推理您的代码了。您的结果差异源于使用d.set_c('b')c.get_c()

dc分别绑定到eDC子对象。

eD子对象中开始查找资源库set_c。这意味着它将查找并关联 setter 的B实例是驻留在D对象中的实例。查找到此为止。

对于 getterget_c,您可以在C子对象中启动查找,因此与 getter 关联的B是驻留在C子对象中的。现在查找到此为止。

正如您已经指出的,这些是不同的子对象,因此 getter 和 setter 不会对相同的数据进行操作。