Wpis z mikrobloga

Kurcze mirki (i mirabelki). To będzie pytanie od laika, ale no nie umiem tego zrozumieć.
Jak to jest z tym dziedziczeniem.
Mam klasę, którą mogę rozszerzyć inną nadrzędną klasę, np. szefa mogę rozszerzyć klasą pracownik gdyż maja metodę wspólną (wypłata ), ale szef dodatkowo ma, np. metodę spotkania służbowe więc szef ma możliwość użycia wszystkich metod pracownika plus dodatkowo swoją własną.
Mogę stworzyć klasę abstrakcyjną, która zawiera metody abstrakcyjne wypłata i spotkania służbowe i użyć tej klasy jako rozszerzenie obu klas, wtedy muszę zaimplementować wszystkie metody abstrakcyjne, ale przy pracowniku nic nie muszę robić z metodą spotkania służbowe , w sensie nie muszę jej nigdzie wywoływać.
Mogę też stworzyć interfejs z metodami wypłata oraz spotkania służbowe .
Wiem, że daną klasę możesz rozszerzyć tylko jedną klasę abstrakcyjną, a wieloma interfejsami.
Kiedy co się używa, co jest prostsze w jaki przypadkach. Pogubiłem się i potrzebowałbym podpowiedzi od kogoś kto z tym obcuje na codzień. Podziękował
#java #naukaprogramowania #programowanie
  • 17
@selenita66: no tak napisałem:

Mam klasę, którą mogę rozszerzyć inną nadrzędną klasę, np. szefa mogę rozszerzyć klasą pracownik gdyż maja metodę wspólną (wypłata ), ale szef dodatkowo ma, np. metodę spotkania służbowe więc szef ma możliwość użycia wszystkich metod pracownika plus dodatkowo swoją własną.
RTFM


@hawat: kurczę, akurat mam tak, że najpierw sam próbuję dojść do rozwiązania czytając opracowania, a potem pytam. Po prostu nie widzę praktycznej różnicy między wykorzystywaniem klas abstrakcyjnych a interfejsami.
@non-serviam: to też napisałem na samym końcu mojego wpisu:

Wiem, że daną klasę możesz rozszerzyć tylko jedną klasę abstrakcyjną, a wieloma interfejsami.


ale nie widzę praktycznego zastostowania w takim przypadku tworzenia klas abstrakcyjnych. Jeśli potrzebujemy czegoś co będzie nam rozszerzać klasy to niewygodniej w takim razie jest implementować tylko interfejsy (jeśli chodzi nam tylko o metody)?
@Going34: szybka odpowiedź od praktyka: gdzie możesz używaj interfejsów a nie klas abstrakcyjnych

w teorii: interfejs ma udostępniać właśnie "interfejs" opisujący jakieś zachowania albo cechy (stąd często forma imiesłowowa(?) typu Runnable, Writable itp) a klasa abstrakcyjna jest czymś pomiędzy bo umożliwia jednocześnie definicję interfejsu jak i implementację go wykorzystującą (trochę taki wzorzez Template Method bez rozdrabniania się na pliki), ale w praktyce klasa abstrakcyjna jest bardzo nieprzyjemna w testowaniu - zarówno
@Going34: Interfejsy stanowią opis kontraktu, czyli co dana klasa implementująca owy interfejs potrafi robić (jakie ma metody) - ale bez szczegółów tego jak te metody działają. Np masz interfrejs KonwerterTekstu z metodą konwertuj(String text) i implementuje go klasa KonwertujDoPdf i KonwertujDoJpg, każda z nich konwertuje do odpowiedniego formatu (#!$%@?ąc w jaki sposób skonwertować text na jpg)

Klasę abstrakcyjną, której już się praktycznie nie używa w dobrych projektach, wprowadzasz jak masz jakąś
@Going34: już ci odpowiedzili chłopacy to się nie bedę rozpisywał ( ͡° ͜ʖ ͡°)
Nie zawracaj sobie za mocno głowy tym na tym etapie, bo to się wydaje niepotrzebne albo bez sensu ale im dalej w las tym bardziej będziesz widział i rozumiał dlaczego tak, a nie inaczej.
Teraz to tylko namącisz sobie w głowie.
@Going34: Spotkania służbowe i wypłata to zupełnie inne konteksty. To, że spotkania możesz przypisać do szczególnego typu osoby wcale nie znaczy, że zachodzi dziedziczenie.
Generalnie dopisywanie metod do podklasy wychodzi poza abstrakcyjne typowanie - to zawsze jest "hack", a nigdy "design" - może coś ułatwić proceduralnie, ale dodaje potencjalny koszt obsługi szczególnych przypadków (if (x instanceof y) ...).

Klasa abstrakcyjna opiera się w zasadzie na dwóch podobnych wzorcach projektowych
@Going34: Dziedziczenie w praktyce się uzywa już bardzo rzadko (zgodnie z Composition over inheritance). Interfejsy z kolei powinno używać się często i najlepiej w jak najdrobniejszej formie (w myśl zasady segregacji interfejsów z SOLID).

Co do przykladow dziedziczenia, to każdy kwadrat jest prostokątem, ale nie każdy prostokat kwadratem, stad kwadrat dziedziczy po prostokącie. Z punktu widzenia impelentacji oczekiwałbym jednak użycie interfejsuow Figura (z metodami obliczania pola i objętości) i Prostokąt z