zxy*_*122 7 c++ constructor virtual-functions stdbind
这是我的代码片段:
class Base {
public:
Base() {
foo();
bind();
}
virtual void foo() {
std::cout << "base foo\n";
}
void bind() {
fn = std::bind(&Base::foo, this);
};
std::function<void()> fn;
};
class Derived : public Base {
public:
void foo() override {
std::cout << "derived foo\n";
}
void bind() {
}
int val;
};
int main() {
Base* p = new Derived();
p->fn();
}
Run Code Online (Sandbox Code Playgroud)
输出是:
class Base {
public:
Base() {
foo();
bind();
}
virtual void foo() {
std::cout << "base foo\n";
}
void bind() {
fn = std::bind(&Base::foo, this);
};
std::function<void()> fn;
};
class Derived : public Base {
public:
void foo() override {
std::cout << "derived foo\n";
}
void bind() {
}
int val;
};
int main() {
Base* p = new Derived();
p->fn();
}
Run Code Online (Sandbox Code Playgroud)
foo()打印,因为根据此问题base foo下的答案,此时 vtable 仍然指向。Base::foo
在 的构造过程中Base,该对象还不是Derived类。那么,调用时std::bind()指针this仍然是类的指针Base,而实参指针是在构造函数体内传递的Base,那么为什么要在类中p->fn调用呢?fooDerived
我的编译器是Apple clang版本14.0.3
std::bind(或任何其他使用指向成员函数的指针,其中所讨论的成员函数是virtual)不绑定到特定函数。相反,当与虚拟成员函数一起使用时,它绑定到虚拟调度槽1(即使用 vtable 的常见实现上的 vtable 槽)。
所以当vtable被更多的派生构造函数重新配置后,通过结果函子找到的函数就会bind发生变化。
1导致成员函数指针类型过大的原因有很多,其中不仅仅包含代码地址,而且能够虚拟分派的需求就是其中之一。
当调用std::bind时仍然是一个指向Base类的指针,并且参数指针是在Base的构造函数体内传递的,为什么p->fn在派生类中调用foo?
一旦Derived调用构造函数,每个指向 的指针现在Base都是指向 的指针Derived。从该位置访问的 vtable 现在是派生 vtable
这就是动态调度的“动态”部分。
| 归档时间: |
|
| 查看次数: |
148 次 |
| 最近记录: |