【问题标题】:Refrence to ... is ambigous!! / C++对...的引用是模棱两可的! / C++
【发布时间】:2021-12-14 03:37:04
【问题描述】:
#include <iostream>

using namespace std;

class Student
{
protected:
    long studentID;
public:
    void setStudentID(long s_){ studentID = s_; }
    Student(): studentID(0){}
    long get_StudentID(){ return studentID; }
};

class Exam : public Student
{
protected:
    float mark;
public:
    void setMark(float m_){ mark = m_; }
    Exam(): mark(0){}
    float getMark(){ return mark; }
};

class Sports : public Student
{
protected:
    float score;
public:
    void setScore(float s_){ score = s_; }
    Sports(): score(0){}
    float getScore(){ return score; }
};

class Result: public Student, public Exam, public Sports
{
private:
    float Total;
public:
    float getTotal(){ return getMark() * getScore(); }
    void display();
};

void Result::display()
{
    cout << "Student ID = " << get_StudentID() << endl;
    cout << "Exam Mark = " << getMark() << endl;
    cout << "Sports Score = " << getScore() << endl;
    cout << "Total Mark = " << getTotal();
}

int main()
{
    Result st1;
    st1.display();
    return 0;
}

我在 Code::Blocks 中编写了这段代码,但它还不完整,但是这个错误说“对 get_StudentID 的引用不明确”让我感到困惑;它出什么问题了? 我应该删除 using namespace 并在所有 (cout, cin & endl) 语句之前插入 std:: 吗?

【问题讨论】:

  • 首先,Sports、anExamResult 都不是Student,所以它们都不应该从Student 继承。仅当派生类与其继承的类具有 is a 关系时,才应从类派生。
  • 为什么你的类都继承自Student?无论如何,get_StudentID() 是模棱两可的,因为您多次(直接和间接)从 Student 继承
  • 继承不是金锤。您的代码架构是错误的。相反,继承使用组合。
  • 当您在Result::display 例程中调用get_StudentID() 时,您期望哪个get_StudentIDStudent::get_StudentID() 一,Exam::Student::get_StudentID() 一,还是Sports::Student::get_StudentID() 一?该代码是使用继承作为金枪的示例。

标签: c++


【解决方案1】:

你误解了继承。比如Exam这个类

class Exam : public virtual Student

从 Student 公开继承。公共继承只能用于IS-A 关系。在这种情况下,Exam 不是 Student,因此您不应使用公共继承。 Sports 也是如此。

“调用不明确”意味着当您从Result 调用get_StudentID 时,编译器无法在Exam::get_StudentIDSports::get_StudentID 之间做出决定,它们都继承自Student

相反:
删除继承,不要在这里的任何地方使用继承。我将完全重新制作它并使用ExamSports 成员对象(如果需要,稍后可以成为对象的向量)创建一个Student 类,并从成员对象中调用所需的函数。 作为一般提示,除非完全必要,否则应避免多重继承。

【讨论】:

  • 我同意,但“作为一般提示,除非完全必要,否则应避免多重继承。”似乎有点限制。有使用多重继承的指南(例如:C.135 - C.136
  • @Ben_LCDB 同意。我想避免是一个强有力的词。 “考虑替代方案”可能会更好
【解决方案2】:

这很容易解决

  1. 从结果基类中删除学生
  2. 让学生 public virtual 参加考试和体育课
#include <iostream>

using namespace std;

class Student
{
protected:
    long studentID;
public:
    void setStudentID(long s_){ studentID = s_; }
    Student(): studentID(0){}
    long get_StudentID(){ return studentID; }
};

class Exam : public virtual Student
{
protected:
    float mark;
public:
    void setMark(float m_){ mark = m_; }
    Exam(): mark(0){}
    float getMark(){ return mark; }
};

class Sports : public virtual Student
{
protected:
    float score;
public:
    void setScore(float s_){ score = s_; }
    Sports(): score(0){}
    float getScore(){ return score; }
};

class Result: public Exam, public Sports
{
private:
    float Total;
public:
    float getTotal(){ return getMark() * getScore(); }
    void display();
};

void Result::display()
{
    cout << "Student ID = " << get_StudentID() << endl;
    cout << "Exam Mark = " << getMark() << endl;
    cout << "Sports Score = " << getScore() << endl;
    cout << "Total Mark = " << getTotal();
}

int main()
{
    Result st1;
    st1.display();
    return 0;
}

天箭:https://godbolt.org/z/4f5n8M5of

【讨论】:

  • 这里没有任何继承意义。考试可能与学生相关联,但不是学生本身。
  • 我只是在回答 C++ 逻辑问题,而不是他们作业的整体优点。
猜你喜欢
  • 2015-08-09
  • 1970-01-01
  • 2010-11-18
  • 1970-01-01
  • 2015-09-20
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多