C++ - 未正确调用覆盖方法(内存冲突)

C++ - Overriden method not called properly (memory violation)

在我的程序中,我试图创建名为“DMA”的抽象 class,“BaseDMA”从它继承。然后 classes "LacksDMA" 和 "HasDMA" 继承自 "BaseDMA"。 每个 class 覆盖方法 readInfo() 来自“DMA”。这是代码:

dma.h

#ifndef DMA_H_
#define DMA_H_

#include <iostream>

class DMA
{
    protected:
        char * label;
    public:
        DMA(const char * l); 
        DMA & operator=(const DMA & anotherDMA);
        virtual ~DMA();
        virtual void readInfo() const = 0;
        char * getLabel() const ;
};

class BaseDMA: public DMA
{
    private: 
        int rating;
    public:
        BaseDMA(const char * l,  int r = 0);
        BaseDMA(const BaseDMA & anotherBaseDMA);
        virtual ~BaseDMA();
        BaseDMA & operator=(const BaseDMA & anotherBaseDMA);
        void readInfo() const override;
};

class LacksDMA: public BaseDMA
{
    private:
        enum { COL_LEN = 40 };
        char color[COL_LEN];
    public:
        LacksDMA(const char * c = "no color", const char * l = "no color", int r = 0);
        LacksDMA(const LacksDMA & anotherLacksDMA);
        LacksDMA & operator=(const LacksDMA & anotherLacksDMA);
        void readInfo() const override;
};

class HasDMA: public BaseDMA
{
    private:
        char * style;
    public:
        HasDMA(const char * s = "lack", const char * l = "lack", int r = 0);
        HasDMA(const HasDMA & anotherHasDMA);
        ~HasDMA();
        HasDMA & operator=(const HasDMA & anotherHasDMA);
        void readInfo() const override;
};

#endif DMA_H_

dma.cpp

#include <string.h>

DMA::DMA(const char * l)
{
    this->label = new char[strlen(l)+1];
    strcpy(this->label, l);
}


DMA & DMA::operator=(const DMA & anotherDMA)
{
    if(this == &anotherDMA)
        return * this;
    delete [] this->label;
    this->label = new char[strlen(anotherDMA.label)+1];
    strcpy(this->label, anotherDMA.label);
    return *this;
}

char * DMA::getLabel() const
{
    return this->getLabel();
}

DMA::~DMA()
{ 
    delete [] label;
}

BaseDMA::BaseDMA(const char * l,  int r)
    : DMA(l)
{
    this->rating = r;
}

BaseDMA::BaseDMA( const BaseDMA & anotherBaseDMA)
    : DMA(anotherBaseDMA.label)
{
    this->rating = anotherBaseDMA.rating;
}

BaseDMA::~BaseDMA()
{

} 

BaseDMA & BaseDMA::operator=(const BaseDMA & anotherBaseDMA)
{
    if(this == &anotherBaseDMA)
        return *this;
    DMA::operator=(anotherBaseDMA);
    this->rating = anotherBaseDMA.rating;
    return *this;
}

void BaseDMA::readInfo() const
{
   std::cout << "BaseDMA object:\n";
   std::cout << "Label: " << this->getLabel() << std::endl;
   std::cout << "Rating: " << this->rating << std::endl;
}


LacksDMA::LacksDMA(const char * c, const char * l, int r)
    :BaseDMA(l,r)
{
    strcpy(this->color, c);
}

LacksDMA::LacksDMA(const LacksDMA & anotherLacksDMA)
    : BaseDMA(anotherLacksDMA)
{
    strcpy(this->color, anotherLacksDMA.color);
}

LacksDMA & LacksDMA::operator=(const LacksDMA & anotherLacksDMA)
{
    if(this == &anotherLacksDMA)
        return *this;
    DMA::operator=(anotherLacksDMA);
    strcpy(this->color, anotherLacksDMA.color);
    return * this;
}

void LacksDMA::readInfo() const
{
    BaseDMA::readInfo();
    std::cout << "LacksDMA object:\n";
    std::cout << "Color: " << color << std::endl;
}

HasDMA::HasDMA(const char * s, const char * l, int r)
    :BaseDMA(l, r)
{
    this->style = new char[strlen(s)+1];
    strcpy(this->style, s);
}

HasDMA::HasDMA(const HasDMA & anotherHasDMA)
    :BaseDMA(anotherHasDMA)
{
    this->style = new char[strlen(anotherHasDMA.style)+1];
    strcpy(this->style, anotherHasDMA.style);
}

HasDMA::~HasDMA()
{
    delete [] this->style;
}

HasDMA & HasDMA::operator=(const HasDMA & anotherHasDMA)
{
    if(this == &anotherHasDMA)
        return *this;
    BaseDMA::operator=(anotherHasDMA);
    delete [] this->style;
    this->style = new char[strlen(anotherHasDMA.style)+1];
    strcpy(this->style, anotherHasDMA.style);
    return *this;
}
void HasDMA::readInfo() const
{
    BaseDMA::readInfo();
    std::cout << "HasDMA object:\n";
    std::cout << "Style: " << this->style << std::endl;

}

main.cpp

#include "dma.h"

void menuPanel();
void printDMS(DMA ** dms, int count);
int main()
{
    const int DMA_COUNT = 4;
    DMA * dmas[DMA_COUNT]; 
    for(int i = 0; i < DMA_COUNT; i++)
    {
        void menuPanel();
        int choice;
        do
        {
            (std::cin >> choice).ignore();
            if(std::cin.bad())
                std::cin.clear();
        } while (choice < 1 || choice > 3);
        
        std::cout << "Write label: ";
        char label[40];
        std::cin.getline(label, 40);
        std::cout << "Write rating: ";
        int rating;
        (std::cin >> rating).ignore();
        if(choice == 1)
        {
            dmas[i] = new BaseDMA(label,rating);
            std::cout << std::endl;
        }
        else if(choice == 2)
        {
            std::cout << "Write color: ";
            char color[40];
            std::cin.getline(color,40);
            dmas[i] = new LacksDMA(color, label, rating);
        }
        else // choice == 3
        {
            std::cout << "write style: ";
            char style[40];
            std::cin.getline(style,40);
            dmas[i] = new HasDMA(style, label, rating);
        }
    }
    for(int i = 0; i < DMA_COUNT; i++)
        delete dmas[i];
    
}

void menuPanel()
{
    std::cout << "Panel action:\n";
    std::cout << "1) make BbaseDMA" << std::endl;
    std::cout << "2) make LacksDMA" << std::endl;
    std::cout << "3) make HasDMA" << std::endl;
    std::cout << std::endl;
}

void printDMS(DMA **  dms, int count)
{
    for(int i = 0; i < count; i++)
    {
        dms[i]->readInfo();
        std::cout << std::endl;
    }
}

当我尝试通过调用 main() 中的 readInfo() 方法来使用运行时多态性时,我收到有关内存冲突的消息。 我做错了什么? 预先感谢您的回答。

您的代码有很多问题,但您的内存问题出在这里:

char * DMA::getLabel() const
{
    return this->getLabel();
}

一旦调用 getLabel(),例如在 BaseDMA::readInfo() 中,您将进入一个无限递归循环,最终溢出调用堆栈。

DMA::getLabel() 应该返回 this->label 而不是:

char * DMA::getLabel() const
{
    return this->label;
}