Jeśli typ implementuje dwa interfejsy, a każdy z nich interfacedefiniuje metodę o identycznej sygnaturze, to w efekcie istnieje tylko jedna metoda i nie można ich rozróżnić. Jeśli, powiedzmy, dwie metody mają sprzeczne typy zwrotów, oznacza to błąd kompilacji. Jest to ogólna zasada dziedziczenia, zastępowania metod, ukrywania i deklaracji, i ma zastosowanie również do ewentualnych konfliktów nie tylko między 2 odziedziczonymi interfacemetodami, ale także metodą interfacesuper i super class, a nawet po prostu konfliktów spowodowanych usunięciem typów ogólnych.
Przykład kompatybilności
Oto przykład, w którym masz metodę interface Gift, która ma present()metodę (jak w, prezentowanie prezentów), a także interface Guest, która również ma present()metodę (jak w, gość jest obecny i nieobecny).
Presentable johnnyjest zarówno Gifta Guest.
public class InterfaceTest {
interface Gift { void present(); }
interface Guest { void present(); }
interface Presentable extends Gift, Guest { }
public static void main(String[] args) {
Presentable johnny = new Presentable() {
@Override public void present() {
System.out.println("Heeeereee's Johnny!!!");
}
};
johnny.present(); // "Heeeereee's Johnny!!!"
((Gift) johnny).present(); // "Heeeereee's Johnny!!!"
((Guest) johnny).present(); // "Heeeereee's Johnny!!!"
Gift johnnyAsGift = (Gift) johnny;
johnnyAsGift.present(); // "Heeeereee's Johnny!!!"
Guest johnnyAsGuest = (Guest) johnny;
johnnyAsGuest.present(); // "Heeeereee's Johnny!!!"
}
}
Powyższy fragment kompiluje się i uruchamia.
Pamiętaj, że jest tylko jedna @Override konieczna !!! . To dlatego, że Gift.present()i Guest.present()są " @Override-equivalent" ( JLS 8.4.2 ).
Tak więc, johnny ma tylko jedną implementację o present(), i to nie ma znaczenia, w jaki sposób leczyć johnny, czy jako Giftlub jako Guest, że jest tylko jeden sposób, aby wywołać.
Przykład niezgodności
Oto przykład, w którym dwie odziedziczone metody NIE są @Overriderównoważne:
public class InterfaceTest {
interface Gift { void present(); }
interface Guest { boolean present(); }
interface Presentable extends Gift, Guest { } // DOES NOT COMPILE!!!
// "types InterfaceTest.Guest and InterfaceTest.Gift are incompatible;
// both define present(), but with unrelated return types"
}
To jeszcze bardziej przypomina, że dziedziczenie członków po konieczności interfacemusi być zgodne z ogólną zasadą deklaracji członków. Tutaj mamy Gifti Guestdefiniujemy present()niekompatybilne typy zwrotów: jeden voiddrugi boolean. Z tego samego powodu, że nie można void present()oraz boolean present()w jednym rodzaju, przykład ten powoduje błąd kompilacji.
Podsumowanie
Możesz dziedziczyć metody, które są @Overrideekwiwalentne, z zastrzeżeniem zwykłych wymagań zastępowania i ukrywania metod. Ponieważ SĄ @Override -equivalent, skutecznie istnieje tylko jeden sposób do wdrożenia, a więc nie ma nic do odróżnienia / wyboru.
Kompilator nie musi określać, która metoda jest przeznaczona dla @Overridedanego interfejsu, ponieważ po ustaleniu , że są równoważne, są one tą samą metodą.
Rozwiązanie potencjalnych niezgodności może być trudnym zadaniem, ale to zupełnie inna kwestia.
Bibliografia