Tworzę interfejs w Javie dla niestandardowej procedury obsługi błędów.
Chcę przekazać obiekt błędu argumentu, ale potrzebuję go, aby był dzieckiem Exception
klasy.
Czy mogę używać mojej zdefiniowanej nazwy klasy w interfejsie?
Czy nie zmniejszy to interfejsu, ponieważ nie będzie zależny od żadnej implementacji?
Próbuję zrobić coś takiego:
public class CustomException {
/* ... Implementation ... */
}
public interface Interface {
void onError(CustomException ex);
}
java
design
object-oriented
interfaces
nikachx
źródło
źródło
CustomException
częścią implementacji czy częścią interfejsu?String
bezpieczniejszy niżCustomException
? Dlaczego ma to znaczenie, jeśliCustomException
z kolei ma inne zależności?Odpowiedzi:
Najpierw muszę zwrócić uwagę na fakt, że
CustomException
to się nie rozszerza,Exception
więc tak naprawdę nie jestException
.To mówi:
Jeśli nie zależy ci na zasadzie odwrócenia zależności , pozostaw ją taką, jaka jest. Jest całkowicie OK, aby interfejs zależał od konkretnych klas, na przykład wiele interfejsów zależy od
String
lubObject
które są klasami konkretnymi . Chodzi o to, że wierzymy, że klasy należące do Java SDK są bardziej stabilne (mniej podatne na zmiany w łamaniu kodu) niż te, które piszemy.W drugiej ręce:
Jeśli chcesz postępować zgodnie z DIP (który ma niezliczone korzyści i jest moją rekomendacją), musisz zrobić jedną z dwóch rzeczy:
opcja 1
CustomException
streszczenievoid onError(CustomException ex)
jak jestOpcja 2
CustomException
interfejsvoid onError(CustomException ex)
jak jestZ każdą z tych opcji będziesz zgodny z DIP, ponieważ interfejs nie będzie zależał od żadnej konkretnej klasy, tylko od abstrakcji.
źródło
Interface
interfejs akceptuje aCustomException
i pozostawia programowi wywołującemu zapewnienie go, osoba dzwoniąca może udostępnić dowolną klasę, która rozciąga się,CustomException
nawet jeśliCustomException
jest to konkretna klasa - co nie byłoby możliwe, gdybyInterface
był w jakiś sposób odpowiedzialny za tworzenie to. To odwrócenie kontroli, bardziej niż praca z interfejsami (choć to z pewnością pomaga), jest tym, o czym myślę, że w tym wszystkim chodzi.Tulains ma rację - interfejsy cały czas zależą od konkretnych klas. Mają jedynie na celu zawarcie umowy na własne potrzeby. Umowa ta może obejmować pobieranie i zwracanie wszelkiego rodzaju danych.
Pamiętaj, że w językach wyższego poziomu nawet prymitywne typy nie są tak prymitywne. W każdym razie pracujesz z konkretnymi typami!
źródło
Myślę, że z nazwy masz na myśli samą klasę. Jeśli próbujesz podać rzeczywistą nazwę klasy wyjątku , aby zainicjować odpowiedni wyjątek za pomocą Reflection, nie jest to właściwa droga.
Jeśli chcesz użyć niestandardowej klasy w interfejsie, możesz oczywiście używać własnych klas we własnych interfejsach. Klasy stają się częścią publicznego interfejsu twojej biblioteki / API. Struktury danych i wyjątki są dobrym przykładem klas, które są często używane przez interfejsy.
Jeśli musisz użyć różnych wyjątków w zależności od kontekstu, możesz być zainteresowany używaniem ogólnych.
źródło