Реализующий оператор & lt; & lt; для производного класса

Итак, у меня есть базовый класс (Shape) и три производных класса, Circle, Rectangle и Square (Square является производным от Rectangle). Я пытаюсь реализовать оператор<< который просто вызывает правильную функцию отображения для того, что вызвало его. Однако я не думаю, что у меня правильный синтаксис. Вот фрагмент — где я ошибся?

class Shape
{
public:
Shape(double w = 0, double h = 0, double r = 0)
{
width = w;
height = h;
radius = r;
}

virtual double area() = 0;
virtual void display() = 0;

protected:
double width;
double height;
double radius;
};

ostream & operator<<(ostream & out, const Shape & s)
{
s.display(out);
return out;
}

class Rectangle : public Shape
{
public:
Rectangle(double w, double h) : Shape(w, h)
{
}

virtual double area() { return width * height; }
virtual void display()
{
cout << "Width of rectangle: " << width << endl;
cout << "Height of rectangle: " << height << endl;
cout << "Area of rectangle: " << this->area() << endl;
}
};

0

Решение

Ты звонишь display как это:

s.display( out );

Но display определяется как:

vritual void display() = 0;

Функция была объявлена ​​и определена без параметров. Следует принять ссылку на std::ostream в качестве параметра:

virtual void display(std::ostream &) = 0;

Это также должно быть const метод, как вы передаете в const объект через operator << перегрузка:

virtual void display(std::ostream &) const = 0;

Не забывайте, что в определении display Вы должны писать в ostream объект, а не конкретно std::cout,

Вот программа компиляции на Ideone.

0

Другие решения

У вас есть ряд проблем здесь. Во-первых, давайте разберемся с проблемой печати:

ostream & operator<<(ostream & out, const Shape & s)

Здесь вы проходите const Shape, Это означает, что вы можете только позвонить const методы на s вы передаете. Однако вы не пометили ни один из методов в базовом (или производном) классе как const, ни area ни display следует изменить состояние объекта. Во-вторых, вы пытаетесь позвонить s.display(out)прохождение ostream& в display, Подпись функции, которую вы имеете, не отражает это. Итак, сложив все вместе, мы получим:

 virtual double area() const = 0;
virtual void display(ostream& out) const = 0;

У вас также есть некоторые другие проблемы — базовый класс, который не объявляет виртуальный деструктор. Если вы планируете использовать класс полиморфно, это должен есть виртуальный деструктор:

virtual ~Shape() { }

Вам также необходимо изменить ваши методы в производном классе:

 double area() const { return width * height; }

void display(ostream& out) const
{
out << "Width of rectangle: " << width << endl;
out << "Height of rectangle: " << height << endl;
out << "Area of rectangle: " << area() << endl;
}

Обратите внимание, что display в Rectangle всегда печатал cout заранее.

0

Вы почти правильно поняли, вот рабочее решение:

#include <iostream>

using std::cout;
using std::endl;
using std::ostream;

class Shape
{
public:
Shape(double w = 0, double h = 0, double r = 0)
{
width = w;
height = h;
radius = r;
}

virtual ~Shape() {} // Recommended!

virtual double area() const = 0;
virtual void display(ostream & out) const = 0;

protected:
double width;
double height;
double radius;
};

ostream & operator<<(ostream & out, const Shape & s)
{
// Since `s` is `const`, then `display` method should be `const` too.
s.display(out);
return out;
}

class Rectangle : public Shape
{
public:
Rectangle(double w, double h) : Shape(w, h)
{
}

virtual double area() const { return width * height; }
virtual void display(ostream & out)  const
{
// Since `display` method is `const`, then `area` method should be
// `const` too.
out << "Width of rectangle: " << width << endl;
out << "Height of rectangle: " << height << endl;
out << "Area of rectangle: " << this->area() << endl;
}
};void main() {
Rectangle r(1, 2);

cout << r << endl;
}

Пожалуйста, обратите внимание на const квалификаторы, которые обеспечивают const-correctness методов класса. Я добавил несколько полезных комментариев, чтобы вы могли плавно следовать логике. Возьмите это за правило, если метод не изменяет членов класса, то вы должен объявить это const,

0
По вопросам рекламы [email protected]