Obiekt danej klasy możesz tworzyć w krótszy sposób:
#include "pch.h"
#include <iostream>
#include <string>
using namespace std;
int main()
{
for (bool is_end_loop = false; !is_end_loop;)
{
cout << "1. Trojkat" << endl;
cout << "2. Trojkat rownoboczny" << endl;
cout << "3. Prostokat" << endl;
cout << "4. Kwadrat" << endl;
cout << "5. Rownoleglobok" << endl;
cout << "6. Romb" << endl;
cout << "7. Kolo" << endl;
cout << "0. Wyjscie" << endl;
cout << "Wybierz numer: ";
int nr;
cin >> nr;
Fig_plaskie *figura;
switch (nr)
{
case 1:
figura = new Trojkat;
break;
case 2:
figura = new Trojkat_row;
break;
case 3:
figura = new Prostokat;
break;
case 4:
figura = new Kwadrat;
break;
case 5:
figura = new Rownoleglobok;
break;
case 6:
figura = new Romb;
break;
case 7:
figura = new Kolo;
break;
case 0:
is_end_loop = true;
continue;
default:
{
cout << "Nie ma takiego numeru\n\n";
return 1;
}
}
figura->sprawdzamy();
figura->pole();
cout << endl;
delete figura;
}
return 0;
}
Nie używaj goto. Używaj override (pomaga unikać błędów). Klasa bazowa Fig_plaskie powinna mieć wirtualny destruktor. Inaczej gdybyś wykonał delete na Fig_plaskie* to oznacza UB, a w konsekwencji w większości implementacji niewykonanie destruktora klasy pochodnej (+ możliwy wyciek pamięci gdyby takową miałby zwalniać).
Używaj listy inicjacyjnej:
Trojkat::Trojkat(string n, float a, float h)
:nazwa(n), a(a), h(h)
{}
Pobieranie danych od użytkownika bardzo często się pojawia. Byłoby dobrze wydzielić taki fragment do osobnej funkcji (plik pch.cpp zostanie uszczuplony o 100 linii kodu):
float getInput(const string& msg, const string& name)
{
float number;
bool is_bad = true;
do
{
cout << msg << name << ": ";
if (cin >> number)
is_bad = false;
cin.clear();
cin.ignore(numeric_limits<streamsize>::max(), '\n');
} while (is_bad);
return number;
}
Przykład z użyciem dla trójkąta:
}
void Trojkat::sprawdzamy()
{
cout << "Podaj nazwe " << nazwa << ": ";
cin >> nazwa;
a = getInput("Podaj podstawe ", nazwa);
h = getInput("Podaj wysokosc ", nazwa);
}
W kolejnych projektach staraj się rozdzielać warstwę logiki od wczytywania i wyświetlania informacji. Przykładowo teraz każda metoda o nazwie 'pole' zawiera:
cout << endl << "Pole " << nazwa << " wynosi: " << a * h << endl;
Figury mogłyby mieć dodatkowo funkcje zwracające pole i nazwę. Przykład użycia w main (bez powtarzania każdorazowo w każdej z klas):
cout << "\nPole " << figura->getName() << " wynosi: " << figura->area() << "'n";