Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/cplusplus/163.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C++ 构造函数不能是虚拟的_C++_Constructor_Virtual Functions - Fatal编程技术网

C++ 构造函数不能是虚拟的

C++ 构造函数不能是虚拟的,c++,constructor,virtual-functions,C++,Constructor,Virtual Functions,在其中一个例子中,我发现了下面关于构造函数不能是虚拟的原因的描述 我们不能声明虚拟构造函数。我们应该详细说明确切的日期 编译时对象的类型,以便编译器可以分配 特定类型的内存 这个描述正确吗 我尤其对短语感到困惑:,这样编译器就可以分配 该特定类型的内存构造函数不能是虚拟的,因为标准中这么说 标准这么说是因为它没有意义。虚拟构造函数会做什么 在多态性中使用虚拟方法。。。如果还没有对象,多态性应该如何工作 我们应该在编译时指定对象的确切类型,所以 编译器可以为特定类型分配内存 我们应该在编译时指定确

在其中一个例子中,我发现了下面关于构造函数不能是虚拟的原因的描述

我们不能声明虚拟构造函数。我们应该详细说明确切的日期
编译时对象的类型,以便编译器可以分配 特定类型的内存

这个描述正确吗


我尤其对短语感到困惑:
,这样编译器就可以分配

该特定类型的内存

构造函数不能是虚拟的,因为标准中这么说

标准这么说是因为它没有意义。虚拟构造函数会做什么

在多态性中使用虚拟方法。。。如果还没有对象,多态性应该如何工作

我们应该在编译时指定对象的确切类型,所以 编译器可以为特定类型分配内存

我们应该在编译时指定确切的类型,因为我们需要该类型的对象。。。我发现他们的描述也很混乱


此外,在这一段中,它没有说这就是构造函数不能是虚拟的原因。它解释了为什么不应从构造函数调用虚拟方法,但仅此而已。

正如比亚恩自己在他的:

虚拟调用是一种在给定部分信息的情况下完成工作的机制。特别是,“虚拟”允许我们调用一个函数,只知道一个接口,而不知道对象的确切类型。要创建对象,您需要完整的信息。特别是,您需要知道要创建的内容的确切类型。因此,“调用构造函数”不能是虚拟的


这是正确的,尽管我认为它没有抓住要点

构造函数设置虚拟分派,即将正确的指针指向当前类的函数。如果构造函数可以是虚拟的,那么谁会事先设置虚拟构造函数?这将是一个可怕的鸡和蛋的问题

然而,有一种称为“虚拟构造函数”的习惯用法,其中类的静态成员返回带有合适类的基类指针:

class A {
    static A* create();
    virtual ~A();
};

class B : public A { ... };

A* A::create() { return new B(); }

一个构造器如何能够是虚拟的
virtual
表示调用该函数的结果由对象的动态类型决定。在施工之前,没有任何目标可以这样做


教程中的短语,构造器是什么,也是假的。您需要指定确切的类型,否则您声明的内容将不会被视为构造函数,并且不允许使用没有返回类型的函数。

除了前面所说的之外,还有虚拟构造函数设计模式,也称为或工厂函数:

。。。它处理创建对象(产品)的问题,而不指定要创建的对象的确切类别


这个解释一半正确,一半虚假。构造函数不能是虚拟的,因为它根本就没有意义。“这样编译器就可以为特定类型分配内存”或多或少是胡言乱语。我们必须在创建对象时指定类型,因为每个对象都有一个类型。(当然,作为创建对象的一部分,必须根据该类型的大小分配一些内存;但这与指定对象的类型无关)。@MikeSeymour:那么动态创建的对象呢。编译器是否需要知道对象的类型?@?LIUXXPENSEUR:是的,C++对象只能在编译时知道类型时创建。对象仅由声明(包括类型)和新表达式(也包括类型)创建。@LinuxPenseur:否,由程序员在编译时在声明或新表达式中指定它来确定。(例如,
东西t;
新的东西
)。编译器基于此生成代码以分配适当的内存量,并调用正确的构造函数。虚拟构造函数习惯用法用于从基类引用创建对象的副本。按照您的显示方式,它不是很有用。@BjörnPollex:您是说一个虚拟函数,返回调用它的对象的副本,对吗?我在术语“虚拟副本构造函数”中知道这个概念。我所演示的概念对于完全隐藏实现类而不调用代码非常有用。尽管这种情况不涉及任何虚拟的内容(多态返回类型除外)。事实上,要使代码正常工作,
A::create
必须是
静态的
,这与
虚拟的
是互斥的。我刚刚检查过,这两个变量的调用都是虚拟构造函数的习惯用法。尽管您的示例仍然需要修改<代码>A::create必须是虚拟的(或者纯虚拟是
A
是抽象的),并且必须在
B
@BjörnPollex中被重写:是的,
静态的
缺失(而且非常重要),抱歉。编辑。是的,“虚拟构造函数”并不是真正的虚拟的,但是尝试模仿类似于虚拟函数的行为(对基类的函数调用以及对该类的部分了解)。谢谢。请您根据
解释一下,以便编译器可以为特定类型的
分配内存。这个短语对吗?那么动态分配给对象的内存呢?@LinuxPenseur:动态创建对象时,编译器仍然需要知道对象的大小。为此,它需要知道实际的类型。@LinuxPenseur:Bjarne的语句回答说,您的Q,virtualism(动态分派)允许您根据对象的类型调用函数,但是只有在构造函数调用返回后,对象才完全形成,因此,除非对象完全成形,否则你怎么能基于它调用函数?@LinuxPenseur:我100%肯定。这就是为什么不能创建