用C++实现了虚拟函数和继承
implementing virtual function and inheritance in C++
所以我有这些头文件:
形状.h:
class Shape
{
public:
Shape();
virtual ~Shape();
virtual double getArea();
virtual void printDraw();
bool isLegal(Shape shape);
};
Trig.h:
class Trig : public Shape
{
public:
Trig(Point pointA, Point pointB, Point pointC);
virtual ~Trig();
virtual double getArea();//override
virtual void printDraw();//override
bool isLegal(Trig trig);//override
};
但是当我尝试实现Trig.cpp时,我会遇到错误。我试过了:
Trig::Trig(Point pointA, Point pointB, Point pointC) {..}
我浏览了一下互联网,但我似乎没有正确地继承遗产。[我的代码必须有只包括声明的头文件!…赋值的要求!]
我在C++中同时使用继承和虚拟函数是新手[我在Java中使用过继承]
关于虚拟函数。。它们的实现与正常功能相比有什么不同吗?[我理解行为上的差异]。
在评论中,您解释了
“我得到错误:对"Shape::Shape()"的未定义引用;
这意味着您忘记提供该构造函数的实现。
现在,随着技术问题的解决,看看设计。
前两种方法有两个缺点:(1)尽管它们永远不应该突变对象,但它们没有被声明为const
,因此不能在const
对象上调用;(2)get
前缀降低了可读性,更易于键入,没有一般优势。我;我发现get
前缀在一些罕见的情况下作为消歧设备很有用,但所有的用法我都很喜欢;初学者看到的是对Java约定的不适当复制,这在Java中是有意义的,但在C++中却没有。因此,不要使用…
virtual double getArea();
virtual void printDraw();
进行
virtual double area() const;
virtual void print() const;
然后,方法…
bool isLegal(Shape shape);
在很多方面都是错误的…哎哟但让我们;让我们从纯粹的技术开始。
从纯粹的技术角度来看,按值传递参数的效率是不必要的,这会导致每次调用都有一个复制操作。而是通过引用传递对象。并将其作为对const
的引用,以便支持const
对象和右值对象作为自变量:
bool isLegal(Shape const& shape);
接下来,命名:isLegal
是一个不好的名称,因为大多数C++对象都是合法的。比如说,它必须是色情的,并且居住在非西方国家,才能成为非法的。我可以;就我的一生而言,我想不出任何方法来让一个物体变得色情,或者让它位于某个特定的地理区域。
所以,
bool isValid(Shape const& shape);
接下来,在低级别设计中,没有充分的理由将非virtual
方法作为普通成员函数,因为这需要在对象上调用它。但它所需要的所有信息都在普通的争论中。我们可以在派生类中看到这种混淆,其中…
bool isLegal(Trig trig);//override
根本不是重写:从技术上讲,它是函数名的重载,这意味着,只是一个同名的不同函数。有;这里没有虚拟,没有覆盖。这是不需要的。
所以,让它成为static
成员函数,它不必在对象上调用:
static bool isValid(Shape const& shape);
最后,在更高层次的设计中,C++构造函数和析构函数的整个机制都在那里,以避免这种方法和检查。
这个想法是你…
在每个构造函数中建立一个有效的对象。
在每个方法中保持对象的有效性。
然后对象可以简单地;t无效。这种方法被称为单相构造,并且使其“有效的;被称为班级类不变量。它应该由每个构造函数建立,并由每个方法维护。
这意味着,在最终版本中,isValid
函数被删除:它没有工作要做,因为该工作是由构造函数和方法(正确地)完成的。
好吧,单阶段构造有一些技术挑战,特别是如何在基类构造函数中进行派生类特定的初始化。这包含在C++常见问题解答中。它;阅读常见问题解答通常是个好主意。
第一个版本是正确的:
Trig::Trig(Point pointA, Point pointB, Point pointC) {..}
它将编译,但不会链接。原因是已声明为Shape
的无参数构造函数,但未能定义。她添加了一个定义
Shape::Shape() {..}
或者,如果默认构造函数为OK,则从Shape的标头中删除声明。
- C++虚函数继承
- 名称隐藏对静态函数继承的实例使用
- C++ std::vector 中的虚拟析构函数继承
- 具有相同名称的类的构造函数继承
- 多复制构造函数继承中的惊人行为
- CRTP 和复制/移动赋值/构造函数继承
- 复制构造函数继承动态分配的数组
- 谷神星求解器成本函数继承错误:模板可能不是虚拟的
- 无法从 c++ 中的构造函数继承
- 在构造函数继承中使用默认构造函数
- 如何定义从虚拟函数继承的静态函数
- 调用超类函数继承 c++
- 构造函数继承和直接成员初始化
- c++ 不明确的双非虚函数继承
- C++ - 使用私有参数的构造函数继承
- 通过可变参数模板进行C++11构造函数继承
- 使用模板进行函数继承
- C++11构造函数继承和不带参数的构造函数
- 函数继承问题
- C++11 - 构造函数继承