摘要 类 和虚拟方法问题:"cannot allocate an object of abstract type"

Abstract Classes and virtual methods problems: "cannot allocate an object of abstract type"

我有这个 classes:

class IDescriptor
{
public:

    virtual float compare(IDescriptor *D) = 0;
};

class DescHistogram : public IDescriptor
{
public:

    vector<float> desc;
    DescHistogram(vector<float> vd);
    ~DescHistogram();
    float compare(DescHistogram *D);
    // ALL THESE FUNCTIONS ARE IMPLEMENTED IN THE SOURCE CPP FILE.
};

在我的代码中的某个地方我做了这个初始化:

vector<float> hist;
[...] // filling the vector.
DescHistogram *myDesc = new DescHistogram(hist);
point.setDescriptor(myDesc);

编译器给我以下错误:

error: cannot allocate an object of abstract type ‘DescHistogram’
note:   because the following virtual functions are pure within ‘DescHistogram’:
note:   virtual float IDescriptor::compare(IDescriptor*)

我对此有一些疑问:

这个错误的原因是什么? DescHistogram::compare的参数必须是什么类型?我知道它可以是派生类型,不是吗? 抽象需要构造函数 class IDescriptor?

也许这是一个愚蠢的错误,但我没有找到适合我的情况的解决方案。预先感谢您的帮助!

您需要在 DescHistogram 中定义比较函数

根据您在此处编写的内容,您可以为 DescHistogram 定义 compare 的实现(并且不要将其标记为纯 virtual)。

What is the reason of this error?

DescHistogram 没有用兼容的函数覆盖 IDescriptor::compare,所以它仍然是抽象的,无法实例化。

What type must be the parameter of DescHistogram::compare?

IDescriptor,以匹配它覆盖的函数。它必须可以用 base-class 函数接受的任何类型调用,因此不能是更派生的类型。

I understand that it can be a derived type, isn't it?

没有。必须是同一类型。

A constructor is needed by the abstract class IDescriptor?

没有。它已经有一个隐式默认构造函数,不需要任何其他东西作为非抽象派生的一部分实例化 class.

没有在DescHistogram中实现virtual compare()功能。您实现了另一个 compare() 函数:

virtual float compare(IDescriptor *D) = 0; // in class IDescriptor
        float compare(DescHistogram *D);   // in class DescHistogram

另一个 compare() 函数没有实现基础的 virtual 函数,因此 DescHistogram 仍然是抽象的。

如果在派生自 IDescriptor 的不同类型(例如 DescHistogram)之间进行比较没有意义,那么您的代码设计就有缺陷。您仍然可以使用 RTTI 让您的代码工作,即通过

class DescHistogram : public IDescriptor
{
  float compare_self(DescHistogram *D); // tolerates nullptr input
public:
  float compare(IDescriptor *D)
  {
    return compare_self(dynamic_cast<DescHistogram*>(D));
  }
};

但这可能效率低下。此外,compare_self 没有任何合理的独立目的(由于设计缺陷)。