C++ C++;继承和构造函数、析构函数

C++ C++;继承和构造函数、析构函数,c++,inheritance,constructor,destructor,C++,Inheritance,Constructor,Destructor,这编译得很好,但是,我想把子类的构造函数(和析构函数)的实现放在它的cpp文件中,有可能吗?怎么做 我尝试了下面的代码,但它抛出了对vtable for Child的未定义引用 //Parent.h class Parent{ public: Parent(){} ~Parent(){} virtual void func1() = 0; }; //Child.h #include "Parent.h" class Child : public Parent{ int x

这编译得很好,但是,我想把子类的构造函数(和析构函数)的实现放在它的cpp文件中,有可能吗?怎么做

我尝试了下面的代码,但它抛出了对vtable for Child的未定义引用

//Parent.h
class Parent{
public:
   Parent(){}
   ~Parent(){}
   virtual void func1() = 0;
};

//Child.h
#include "Parent.h"
class Child : public Parent{
  int x, y;
public:
  Child() : Parent(){ //constructor

  }
  virtual void func1();
};

//Child.cpp
#include "Child.h"
void Child::Parent::func1(){

}

您需要做几件事:

  • 保护您的头文件以防止意外的多个包含
  • 使父析构函数成为虚拟的
  • 初始化非自动成员变量以确定值
您的最终布局可以如下所示

Parent.h

$ cat Parent.h 
#ifndef GUARD_PARENT_H_
#define GUARD_PARENT_H_

class Parent{
public:
   Parent(){}
   ~Parent(){}
   virtual void func1() = 0;
};

#endif /* GUARD_PARENT_H_ */
$ cat Child.h
#ifndef GUARD_CHILD_H_
#define GUARD_CHILD_H_

#include "Parent.h"

class Child : public Parent{
  int x, y;
public:
  Child();
  virtual void func1();
};

#endif /* GUARD_CHILD_H_ */
$ cat Child.cpp
#include "Child.h"

Child::Child() : Parent() {
}

void Child::func1(){
}
$ cat try.cc
#include "Child.h"

int main() {
        Child c;
}
$ g++ try.cc Child.cpp
$ ./a.out
$
#ifndef PARENT_H_
#define PARENT_H_

class Parent
{
public:
    Parent() {};
    virtual ~Parent() {};

public:
    virtual void func1() = 0;
};

#endif // PARENT_H_
Child.h

$ cat Parent.h 
#ifndef GUARD_PARENT_H_
#define GUARD_PARENT_H_

class Parent{
public:
   Parent(){}
   ~Parent(){}
   virtual void func1() = 0;
};

#endif /* GUARD_PARENT_H_ */
$ cat Child.h
#ifndef GUARD_CHILD_H_
#define GUARD_CHILD_H_

#include "Parent.h"

class Child : public Parent{
  int x, y;
public:
  Child();
  virtual void func1();
};

#endif /* GUARD_CHILD_H_ */
$ cat Child.cpp
#include "Child.h"

Child::Child() : Parent() {
}

void Child::func1(){
}
$ cat try.cc
#include "Child.h"

int main() {
        Child c;
}
$ g++ try.cc Child.cpp
$ ./a.out
$
#ifndef PARENT_H_
#define PARENT_H_

class Parent
{
public:
    Parent() {};
    virtual ~Parent() {};

public:
    virtual void func1() = 0;
};

#endif // PARENT_H_
Child.cpp

#ifndef CHILD_H_
#define CHILD_H_

#include "Parent.h"

class Child : public Parent
{
    int x,y;

public:
    Child();
    virtual ~Child();

    virtual void func1();
};
#endif

+1--但是父级的析构函数应该是
虚拟的
或者
受保护的
。是的,这很好。但在向初学者解释问题时,这是一个陷阱,你不应该只是“照搬问题”。多亏了你们两个。顺便问一下,你所做的叫什么?添加了警卫的东西,这样我就可以在谷歌上搜索并阅读更多关于它的信息。我认为“包括警卫”是常用的名称。(它们在那里是因为我的编辑器在我启动新的
.h
文件时自动添加它们。)拒绝更正虚拟析构函数问题,这不是正确的答案。@markuz我希望这是有意义的。现在就养成初始化成员的习惯。对于引用来说,这是强制性的,并且通常一个可靠的实践是知道即使您的POD类型成员(普通的旧数据)也是用已知值初始化的。