Techniki programowania INP001002Wl rok akademicki 2017/18 semestr letni Wykład 4 Karol Tarnowski karol.tarnowski@pwr.edu.pl A-1 p. 411B
Plan prezentacji Dziedziczenie Przestrzenie nazw Na podstawie: A. Allain, Przewodnik dla początkujących C++ S. Prata, Szkoła programowania C++
Dziedziczenie pozwala dodawać nowe możliwości (nowe metody) do istniejącej klasy Dziedziczenie pozwala dodawać nowe dane do klasy Dziedziczenie pozwala zmieniać działanie metod klasy
Prosta klasa bazowa: przechowuje imię i nazwisko oraz informację o tym, czy gracz ma stół pingpongowy
Klasa pochodna: dodatkowa informacja o punktach rankingowych class RatedPlayer : public TableTennisPlayer {... }; Obiekt klasy pochodnej zawiera w sobie dane składowe typu bazowego. Klasa pochodna dziedziczy implementację klasy bazowej.
Klasa pochodna potrzebuje własnego konstruktora. W klasie pochodnej można dodać nowe pola i metody.
Klasa pochodna nie ma dostępu do prywatnych składowych klasy bazowej, do ich inicjalizacji należy wykorzystać listę inicjalizacyjną
Wskaźniki klasy bazowej mogą pokazywać obiekty klasy pochodnej. Referencja klasy bazowej może odnosić się do obiektu klasy pochodnej.
W konsekwencji funkcje pobierające jako argument referencję do klasy bazowej działają także dla obiektów klasy pochodnej.
RatedPlayer rplayer(1140, "Maciej", "Kaczkowski", true); TableTennisPlayer player("teresa", "Bogatko", false); Show(player); Show(rplayer);
Podobnie można inicjalizować obiekty klasy bazowej za pomocą obiektu klasy pochodnej
Rachunek bankowy imię i nazwisko klienta, numer rachunku, saldo. Operacje na rachunku: tworzenie rachunku, wpłata, wypłata, wyświetlenie.
Rachunek bankowy rozszerzony o: limit debetu, stopa procentowa, zadłużenie. Operacje na rachunku: wypłata (obsługuje powstanie debetu), wyświetlenie (w tym dodatkowych informacji).
W obu klasach zadeklarowano metody withdraw(), viewaccount() Nowe słowo kluczowe virtual W klasie Account jest zadeklarowany także destruktor wirtualny
Konstruktory klasy pochodnej używaj list inicjalizacyjnych Metoda AccountPlus::viewAccount() wywołuje metodę Account::viewAccount() Metoda AccountPlus::withdraw wywołuje, w zależności od sytuacji, różne metody
Account * p_clients[clients];... for(int i=0; i < CLIENTS; i++){ p_clients[i]->viewaccount(); cout << endl; } for(int i=0; i < CLIENTS; i++){ delete p_clients[i]; }
class Account{ protected: double balance;... };
Abstrakcyjna klasa bazowa AccountABC
Przestrzenie nazw Nazwy w języku C++ mogą odnosić się do zmiennych, funkcji, struktur, wyliczeń, klas, składowych struktur i klas Dla rosnących projektów rośnie ryzyko kolizji tych nazw Dodatkowo ryzyko zwiększa się w projektach wykorzystujących biblioteki zewnętrzne. W celu uniknięcia konfliktów wprowadzono mechanizm przestrzeni nazw.
Przestrzenie nazw Polecenie using namespace nazwa_przestrzeni; udostępnia wszystkie nazwy z przestrzeni nazwa_przestrzeni Przykładowo using namespace std; udostępnia wszystkie nazwy z przestrzeni std.
Przestrzenie nazw Polecenie using namespace std; udostępnia wszystkie nazwy z przestrzeni std. Dzięki temu możemy korzystać bezpośrednio z obiektów cout, cin. Nie musimy odwoływać się do pełnych nazw: std::cout, std::cin.
Przestrzenie nazw Definiowanie przestrzeni nazw Przykład namespace cprogramming{ int x; }//brak średnika Dostęp do zmiennej x można uzyskać pisząc cprogramming::x, dołączając całą przestrzeń nazw using namespace cprogramming; lub dołączając tylko wybraną nazwę z przestrzeni using namespace cprogramming::x;
Przestrzenie nazw Zagnieżdżanie przestrzeni nazw Przykład namespace com{ namespace cprogramming { }} int x;
Przestrzenie nazw Przykład do istniejącej przestrzeni nazw namespace com{ } int x; można dodać nowy element... namespace com{ } double y;
Przestrzenie nazw Kiedy stosować instrukcję using namespace Zazwyczaj nie należy umieszczać deklaracji using w plikach nagłówkowych, a tylko w plikach źródłowych. Zalecenie: w plikach nagłówkowych stosuj pełne nazwy, w plikach źródłowych można wykorzystywać deklarację using.
Podsumowanie Dziedziczenie Przestrzenie nazw