C++多重继承-类方法运行两次

问题描述 投票:0回答:1

我有一个练习多重继承和多态性的练习,但有些事情进展不顺利。 该练习包括我需要构建的 4 个类:

  1. 生物
  • 字符 * 名称
  • 年龄
  • int 后代数量
  1. 吸血鬼:生物
  • int 光灵敏度
  • 吸血鬼**后代
  1. 狼人:生物
  • int humanHours
  • int狼人时间
  • 狼人**后代
  1. 吸血鬼狼人:吸血鬼,狼人
  • 生物**后代

有一个名为 printInfo 的方法可以打印出每个类的信息。正如您所期望的,该函数的使用在每个类中都会被覆盖,同时还会打印父母的信息。当我尝试使用 VampireWerewolf 中的 printInfo 时,我得到了 Creature 部分两次,但我不确定应该做什么才能让它运行一次。附上下面的代码

生物.h

#ifndef CREATURE_H
#define CREATURE_H
#include <iostream>
using namespace std;

class Creature {
protected:
    char* m_name;
    int m_age;
    int m_numOfOffsprings;
public:
    // Constructors
    Creature(): m_name(nullptr), m_age(0), m_numOfOffsprings(0) {}
    Creature(const char* name, int age, int numOfOffsprings):
        m_age(age),
        m_numOfOffsprings(numOfOffsprings) {
        m_name = new char[strlen(name) + 1];
        strcpy_s(m_name, strlen(name) + 1, name);
    }

    char* getName() { return m_name; }
    int getAge() { return m_age; }
    int getNumOfOffsprings() { return m_numOfOffsprings; }

    virtual void printInfo() {
        cout << "===Creature printInfo===" << endl << endl;
        cout << "Name: " << m_name << endl;
        cout << "Age: " << m_age << endl;
        cout << "Number of offsprings: " << m_numOfOffsprings << endl;
    }
};

#endif // !CREATURE_H

吸血鬼.h

#ifndef VAMPIRE_H
#define VAMPIRE_H
#include <iostream>
#include <array>
#include "Creature.h"
using namespace std;

class Vampire : public virtual Creature {
    int m_lightSensitivity;
    Vampire** m_offsprings;
public:
    // Constructors
    Vampire(): m_lightSensitivity(0), m_offsprings(nullptr) {}
    Vampire(char* name, int age, int numOfOffsprings, int lightSensitivity, Vampire** offsprings):
        Creature(name, age, numOfOffsprings), m_lightSensitivity(lightSensitivity) {
        if (numOfOffsprings <= 0) { m_offsprings = nullptr; }
        else {
            m_offsprings = new Vampire * [numOfOffsprings];
            for (int i = 0; i < numOfOffsprings; i++) {
                m_offsprings[i] = offsprings[i];
            }
        }
        
    }
    virtual void printInfo() override {
        Creature::printInfo();
        cout << "===Vampire printInfo===" << endl << endl;
        cout << "Light sensitivity: " << m_lightSensitivity << endl;
        for (int i = 0; i < m_numOfOffsprings; i++) {
            cout << "- Offspring " << i + 1 << ": " << m_offsprings[i]->m_name << endl;
        }
    }
};

#endif // !VAMPIRE_H

狼人.h

#ifndef WEREWOLF_H
#define WEREWOLF_H
#include <iostream>
#include "Creature.h"
using namespace std;

class Werewolf: public virtual Creature {
    int m_werewolfHours, m_humanHours;
    Werewolf** m_offsprings;
public:
    // Constructors
    Werewolf() : m_werewolfHours(0), m_humanHours(0), m_offsprings(nullptr) {}
    Werewolf(char* name, int age, int numOfOffsprings, int werewolfH, int humanH, Werewolf** offsprings):
        Creature(name, age, numOfOffsprings),
        m_werewolfHours(werewolfH),
        m_humanHours(humanH) {
        if (numOfOffsprings <= 0) { m_offsprings = nullptr; }
        else {
            m_offsprings = new Werewolf * [numOfOffsprings];
            for (int i = 0; i < numOfOffsprings; i++) {
                m_offsprings[i] = offsprings[i];
            }
        }
    }
    
    virtual void printInfo() override {
        Creature::printInfo();
        cout << "===Werewolf printInfo===" << endl << endl;
        cout << "Werewolf hours: " << m_werewolfHours << endl;
        cout << "Human hours: " << m_humanHours << endl;
        for (int i = 0; i < m_numOfOffsprings; i++) {
            cout << "- Offspring " << i + 1 << ": " << m_offsprings[i]->m_name << endl;
        }
    }
};

#endif // !WEREWOLF_H

吸血鬼狼人.h

#ifndef VAMPIRE_WEREWOLF_H
#define VAMPIRE_WEREWOLF_H
#include <iostream>
#include "Vampire.h"
#include "Werewolf.h"
using namespace std;

class VampireWerewolf : public Vampire, public Werewolf {
    Creature** m_offsprings;
public:
    VampireWerewolf(
        char* name,
        int age,
        int numOfOffsprings,
        int lightSensitivity,
        int werewolfHours,
        int humanHours,
        Creature** offsprings):
        Creature(name, age, numOfOffsprings),
        Vampire(name, age, numOfOffsprings, lightSensitivity, nullptr),
        Werewolf(name, age, numOfOffsprings, werewolfHours, humanHours, nullptr) {
        if (numOfOffsprings <= 0) { m_offsprings = nullptr; }
        else {
            m_offsprings = new Creature * [numOfOffsprings];
            for (int i = 0; i < numOfOffsprings; i++) {
                m_offsprings[i] = offsprings[i];
            }
        }
    }

    virtual void printInfo() {
        Vampire::printInfo();
        Werewolf::printInfo();
                // <Additional VampireWerewolf info below>
    }
};

#endif // !VAMPIRE_WEREWOLF_H

主要.cpp

#include <iostream>
#include "Creature.h"
#include "Vampire.h"
#include "Werewolf.h"
#include "VampireWerewolf.h"
using namespace std;

int main() {
    VampireWerewolf ackbar((char*)"Ackbar", 100, 0, 50, 24, 0, nullptr);
    ackbar.printInfo();
    return 1;
}

我对类和方法使用了虚拟签名,并向 Vampire::printInfo() 和 Werewolf::printInfo() 添加了 override 关键字。

c++ polymorphism multiple-inheritance
1个回答
0
投票

我找到了一种解决方法,将 printInfo 分为两个不同的函数:printCommonInfo专门从 Creature 运行并打印姓名、年龄和 numOfOffsprings 以及 printSpecificInfo从 Vampire 和 Werewolf 运行以仅打印各自的独特成员。当我从 VampireWerewolf 运行 printInfo 时,有一个对 printCommonInfo 的调用,我调用了 Vampire::printSpecificInfo() 和 Werewolf::printSpecificInfo()。

生物:

void printCommonInfo() {
    cout << "===Creature printInfo===" << endl;
    cout << "Name: " << m_name << endl;
    cout << "Age: " << m_age << endl;
    cout << "Number of offsprings: " << m_numOfOffsprings << endl;
}

virtual void printSpecificInfo() = 0;

void printInfo() {
    printCommonInfo();
    printSpecificInfo();
    cout << endl;
}

吸血鬼:

virtual void printSpecificInfo() override {
    cout << "===Vampire printInfo===" << endl;
    cout << "Light sensitivity: " << m_lightSensitivity << endl;
    if (m_offsprings != nullptr) {
        for (int i = 0; i < m_numOfOffsprings; i++) {
            cout << "- Offspring " << i + 1 << ": " << m_offsprings[i]->m_name << endl;
        }
    }
}

狼人:

virtual void printSpecificInfo() override {
    cout << "===Werewolf printInfo===" << endl;
    cout << "Werewolf hours: " << m_werewolfHours << endl;
    cout << "Human hours: " << m_humanHours << endl;
    if (m_offsprings != nullptr) {
        for (int i = 0; i < m_numOfOffsprings; i++) {
            cout << "- Offspring " << i + 1 << ": " << m_offsprings[i]->m_name << endl;
        }
    }
}

吸血鬼狼人:

virtual void printSpecificInfo() override {
    Vampire::printSpecificInfo();
    Werewolf::printSpecificInfo();
    cout << "===VampireWerewolf printInfo===" << endl;
    for (int i = 0; i < m_numOfOffsprings; i++) {
        cout << "- Offspring " << i + 1 << endl;
        cout << "Name: " << m_offsprings[i]->getName() << endl;
        cout << "Species: ";
        if (auto* VOffspring = dynamic_cast<Vampire*>(m_offsprings[i])) {
            cout << "Vampire" << endl;
        }
        else if (auto* WOffspring = dynamic_cast<Werewolf*>(m_offsprings[i])) {
            cout << "Werewolf" << endl;
        }
        else if (auto* VWOffspring = dynamic_cast<VampireWerewolf*>(m_offsprings[i])) {
            cout << "Vampire Werewolf" << endl;
        }
    }
}
© www.soinside.com 2019 - 2024. All rights reserved.