IPB
ЛогинПароль:

> Внимание!

1. Пользуйтесь тегами кода. - [code] ... [/code]
2. Точно указывайте язык, название и версию компилятора (интерпретатора).
3. Название темы должно быть информативным.
В описании темы указываем язык!!!

Наладить общение поможет, если вы подпишитесь по почте на новые темы в этом форуме.

> Классы, наследственность
сообщение
Сообщение #1


Бывалый
***

Группа: Пользователи
Сообщений: 212
Пол: Мужской

Репутация: -  0  +


Есть вот такая программа.

#include <iostream.h>
#include <conio.h>
#include <stdlib.h>
#include <dos.h>
#include <graphics.h>
#include <string.h>
#include <math.h>
void move(int i);
// è½áßß öêâôÉÇ
class Figure
{
protected:
int Color;
int CenterX;
int CenterY;
public:
Figure(int iCenterX, int iCenterY)
{
Color = RED;
CenterX = iCenterX;
CenterY = iCenterY;
}
void SetNewColor(int NewColor)
{
Hide();
Color=NewColor;
Show();
}
virtual void Show() = 0;
virtual void Hide()
{
int prev_col = Color;
Color=getbkcolor();
Show();
Color = prev_col;
}
void Move(int DeltaX, int DeltaY)
{
Hide();
CenterX+=DeltaX;
CenterY+=DeltaY;
Show();
}
virtual ~Figure() {};
};

class Butterfly: public Figure
{
private:
int Radius;
int RadiusX;
int RadiusY;
int Stangle;
int Endangle;
public:
Butterfly(int iCenterX, int iCenterY, int iStangle,int iEndangle,int iRadiusX,int iRadiusY,int iRadius) :
Figure(iCenterX, iCenterY)
{
Stangle=iStangle;
Endangle=iEndangle;
Radius=iRadius;
RadiusX = iRadiusX;
RadiusY = iRadiusY;
}
void Show();
};

class Hexe: public Figure
{
private:
int RRadius;
int rRadius;
public:
Hexe(int iCenterX, int iCenterY, int iRadius) :
Figure(iCenterX, iCenterY)
{
RRadius = iRadius;
rRadius = (sqrt(3)/2)*RRadius;
}
void Show();
};

class Combo:public Hexe,public Butterfly
{
public:
Combo(int iCenterX, int iCenterY, int iStangle,int iEndangle,int iRadiusX,int iRadiusY,int iRadius) :
Hexe( iCenterX, iCenterY, iRadius),Butterfly(iCenterX, iCenterY, iStangle,iEndangle, iRadiusX, iRadiusY,iRadius)
{}
void Show();
void Hide();
void Move(int x);
void SetNewColor(int colr);
~Combo(){};
};

void Hexe::Show()
{
int prev_color=getcolor();
setcolor(Color);
line(CenterX, CenterY+RRadius,CenterX-rRadius,CenterY+RRadius/2);
line(CenterX-rRadius,CenterY+RRadius/2,CenterX-rRadius,CenterY-RRadius/2);
line(CenterX-rRadius,CenterY-RRadius/2,CenterX,CenterY-RRadius);
line(CenterX,CenterY-RRadius,CenterX+rRadius,CenterY-RRadius/2);
line(CenterX+rRadius,CenterY-RRadius/2,CenterX+rRadius,CenterY+RRadius/2);
line(CenterX+rRadius,CenterY+RRadius/2,CenterX, CenterY+RRadius);
setcolor(prev_color);
}

void Butterfly::Show()
{
int prev_color=getcolor();
setcolor(Color);
circle(CenterX, CenterY-RadiusY, Radius/5);
ellipse(CenterX, CenterY+Radius/5, Stangle,Endangle,RadiusX,RadiusY);
line(CenterX-(sqrt(3)/2*Radius),CenterY-Radius/2,CenterX-20,CenterY);
line(CenterX-20,CenterY,CenterX-(sqrt(3)/2*Radius),CenterY+Radius/2);
line(CenterX-(sqrt(3)/2*Radius),CenterY-Radius/2,CenterX-(sqrt(3)/2*Radius),CenterY+Radius/2);
line(CenterX+(sqrt(3)/2*Radius),CenterY-Radius/2,CenterX+20,CenterY);
line(CenterX+20,CenterY,CenterX+(sqrt(3)/2*Radius),CenterY+Radius/2);
line(CenterX+(sqrt(3)/2*Radius),CenterY-Radius/2,CenterX+(sqrt(3)/2*Radius),CenterY+Radius/2);
setcolor(prev_color);
}

void Combo::Show()
{
Butterfly::Show();
Hexe::Show();
}

void Combo::Hide()
{
Butterfly::Hide();
Hexe::Hide();
}

void Combo::Move(int x)
{
Butterfly::Move(15*x,15*x);
Hexe::Move(15*x,15*x);
}

void Combo::SetNewColor(int colr)
{
Butterfly::SetNewColor(colr);
Hexe::SetNewColor(colr);
}

int main()
{ int n_menu;
while (1)
{
clrscr;
cout<<"1-Butterfly\n2-Hexe\n3-Combo\n4-Exit\n";
cin>>n_menu;
int gdriver = DETECT, gmode, errorcode;
initgraph(&gdriver, &gmode,
"../BGI");
errorcode = graphresult();
if (errorcode != grOk)
{
cerr<<"Graphics error";
cerr<<grapherrormsg(errorcode);
exit(1);
}
Butterfly F1(100,100,0,360,20,75,100);
Hexe F2(100,100,100);
Combo F3(100,100,0,360,20,75,100);
switch(n_menu)
{
case 1: cleardevice();F1.Show();break;
case 2: cleardevice();F2.Show();break;
case 3: cleardevice();F3.Show();break;
case 4: cout<<"Bay! Bay!\n";delay(750);return 0;
}
getch();
int maxcolor = getmaxcolor();
int direction = 1;
for (int color = 0; !kbhit(); color++)
{
if (color>maxcolor)
{color=0; direction*=-1;}

switch (n_menu)
{
case 1: F1.SetNewColor(color);F1.Move(10*direction,10*direction);break;
case 2: F2.SetNewColor(color);F2.Move(10*direction,10*direction);break;
case 3: F3.SetNewColor(color);F3.Move(direction);break;
}
delay(50);
}
closegraph();
}
}


По меню по очереди можно вывести бабочку, потом шестиугольник правильный, потом комбинированно бабочку в шестиугольнике. Бабочки и шестиугольник наследники от общего класса фигуры, а вот комбо от бабочки и шестиугольника. Не пойму вот следующее по идее класс Combo должен ведь унаследовать методы Move и SetNewColor, так как он наследник от Butterfly и Hex, которые в свою очередь наследуют данный метод от Figure. Но если выкинуть эти методы как сделано в выше представленном коде и напрямую обращаться например F3.SetNewColor(color);F3.Move(10*direction,10*direction); естественно компилятор материться. Так как правильно оформить наследственность и добраться до данных методов, не прописывая их в классе Combo и естественно не описывая так
void Combo::Move(int x)
{
Butterfly::Move(15*x,15*x);
Hexe::Move(15*x,15*x);
}

void Combo::SetNewColor(int colr)
{
Butterfly::SetNewColor(colr);
Hexe::SetNewColor(colr);
}


P.S. Как в спойлер код скрывать, а то как то не красиво длинный пост получается?
 Оффлайн  Профиль  PM 
 К началу страницы 
+ Ответить 
 
 Ответить  Открыть новую тему 
Ответов
сообщение
Сообщение #2


Гуру
*****

Группа: Пользователи
Сообщений: 1 013
Пол: Мужской
Ада: Разработчик
Embarcadero Delphi: Сторонник
Free Pascal: Разработчик

Репутация: -  627  +


Цитата
преподаватель говорит зачем создавать методы void Hide(); void Move(int x); void SetNewColor(int colr); у данного класса, ведь они наследуются. Вот мне интересно как их использовать без создания а по наследству
Преподаватель в своем уме? При множественном наследовании методов (да еще и виртуальных) с одинаковыми именами и с одной областью видимости (они все описываются в public-разделе, и наследование всегда общее, то есть все они видимы в потомках) возникает неоднозначность, которую компилятор не имеет права разрешать. Скажем:

#include <iostream>

class A
{
public:
virtual void f()
{
std::cout << "A::f()" << std::endl;
}
};

class B
{
public:
virtual void f()
{
std::cout << "A::f()" << std::endl;
}
};

class C : public A, public B
{
public:
C() : A(), B() { }
};

int main()
{
C obj;
obj.f(); // Какую из функций надо вызывать? Может одну, может обе. Тогда в каком порядке?
return 0;
}

Так что даже не выдумывай, без переопределения в классе Combo этой "прослойки" не обойдешься. Кстати, Липпман именно такой способ называет хорошим тоном программирования.

Но у тебя есть еще одна загвоздка.

Еще раз смотри: (Показать/Скрыть)


Оно тебе надо, чтоб базовый класс инициализировался 2 раза? Не надо.

Решение: (Показать/Скрыть)
Чувствуешь разницу?
 Оффлайн  Профиль  PM 
 К началу страницы 
+ Ответить 

Сообщений в этой теме


 Ответить  Открыть новую тему 
1 чел. читают эту тему (гостей: 1, скрытых пользователей: 0)
Пользователей: 0

 





- Текстовая версия 6.05.2024 8:44
500Gb HDD, 6Gb RAM, 2 Cores, 7 EUR в месяц — такие хостинги правда бывают
Связь с администрацией: bu_gen в домене octagram.name