Java Interfaces/Implementation naming convention [duplicate]

To pytanie ma już odpowiedź tutaj:

Jak nazwać różne klasy / interfejsy, które tworzysz? Czasami nie mam informacji o implementacji do interfejsu o nazwie implementacyjnej FileHandler I klasy SqlFileHandler.

Kiedy tak się dzieje, zwykle nazywam interfejs w "normalna" Nazwa, jak Truck i nazwa rzeczywistej klasy TruckClass.

Jak nazwać interfejsy i klasy w tym zakresie?

Author: Joshua Taylor, 2010-05-12

9 answers

Nazwij swoje Interface co to jest. Truck. Nie ITruck ponieważ to nie jest ITruck to jest Truck.

An Interface w języku Java jest typem . Więc masz DumpTruck, TransferTruck, WreckerTruck, CementTruck, etc that implement Truck.

Kiedy używasz Interface zamiast podklasy, po prostu rzucasz ją do Truck. Jak w List<Truck>. Wstawianie I z przodu jest po prostu Węgierski styl notacjatautologia , która dodaje do kodu tylko więcej rzeczy do wpisania.

Wszystkie nowoczesne Java IDE Oznacz Interfejsy i implementacje i co nie bez tej głupiej notacji. Nie nazywaj tego TruckClass to jest tautologia tak samo zła jak IInterface tautologia.

Jeśli jest implementacją, to jest klasą. Jedynym prawdziwym wyjątkiem od tej reguły, i zawsze są wyjątki, może być coś w rodzaju AbstractTruck. Ponieważ tylko podklasy kiedykolwiek to zobaczą i nigdy nie powinieneś rzucać do klasy Abstract, dodaje to pewne informacje, że klasa jest abstrakcyjna i jak powinna być używany. Możesz wymyślić lepszą nazwę niż {[17] } i zamiast tego użyć BaseTruck lub DefaultTruck, ponieważ abstract jest w definicji. Ale ponieważ Abstract klasy nigdy nie powinny być częścią żadnego publicznego interfejsu, uważam, że jest to akceptowalny wyjątek od reguły. Tworzenie konstruktorów protected prowadzi długą drogę do przekroczenia tej przepaści.

I Impl przyrostek jest po prostu więcej hałasu, jak również. Więcej tautologii. Wszystko, co nie jest interfejsem, jest implementacją, nawet abstrakcyjne klasy, które są implementacjami częściowymi. Czy zamierzasz umieścić ten głupi przyrostek Impl na każdej nazwie każdej klasy ?

{[0] } jest kontraktem na to, co mają do obsługi publiczne metody i właściwości, jest to równieżTyp Informacje. Wszystko, co implementuje Truck jest typem z Truck.

Spójrz na samą bibliotekę standardową Javy. Czy widzisz IList, ArrayListImpl, LinkedListImpl? Nie, widzisz List i ArrayList i LinkedList. Oto ładny artykuł o tym pytaniu. Każda z tych głupich konwencji nazewnictwa przedrostków/sufiksów narusza zasadę DRY.

Również, jeśli znajdziesz się dodanie DTO, JDO, BEAN lub inne głupie powtarzające się przyrostki do obiektów, które prawdopodobnie należą do pakietu zamiast wszystkich tych przyrostków. Odpowiednio zapakowane przestrzenie nazw są samodokumentujące się i zmniejszają wszystkie bezużyteczne zbędne informacje w tych naprawdę słabo pomyślanych systemach nazw zastrzeżonych, które najbardziej miejsca nawet wewnętrznie nie przylegają do siebie w sposób spójny.

Jeśli wszystko, co możesz wymyślić, aby Twoja nazwa Class była unikalna, to wystarczy ją przyrostkiem Impl, to musisz przemyśleć posiadanie Interface w ogóle. więc kiedy masz sytuację, w której masz Interface i pojedynczy Implementation, który nie jest specjalnie wyspecjalizowany od Interface prawdopodobnie nie potrzebujesz Interface.

 762
Author: feeling abused and harassed,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2018-09-04 17:36:02

Widziałem tutaj odpowiedzi, które sugerują, że jeśli masz tylko jedną implementację, to nie potrzebujesz interfejsu. Jest to sprzeczne z zasadą Depencency Injection/Inversion of Control (nie dzwoń do nas, zadzwonimy do ciebie!).

Więc tak, są sytuacje, w których chcesz uprościć swój kod i uczynić go łatwym do przetestowania, opierając się na implementacjach interfejsu (które mogą być również proxy-Twój kod nie wie!). Nawet jeśli masz tylko dwie implementacje - jedną makieta do testowania i taka, która jest wtryskiwana do rzeczywistego kodu produkcyjnego - to nie sprawia, że posiadanie interfejsu jest zbędne. Dobrze udokumentowany interfejs ustanawia umowę, która może być również utrzymywana przez ścisłą implementację mock do testowania.

W rzeczywistości, można ustanowić testy, które mają mocks zaimplementować najbardziej rygorystyczny kontrakt interfejsu (rzucanie wyjątków dla argumentów, które nie powinny być null, itp) i wychwycić błędy w testowaniu, używając bardziej wydajnej implementacji w kodzie produkcyjnym (Nie sprawdzanie argumentów, które nie powinny być null, ponieważ mock wyrzucił wyjątki w testach i wiesz, że argumenty nie są null z powodu naprawiania kodu po tych testach, na przykład).

Dependency Injection / IOC może być trudne do uchwycenia dla nowicjusza, ale gdy zrozumiesz jego potencjał, będziesz chciał go używać wszędzie i będziesz robił interfejsy cały czas - nawet jeśli będzie tylko jeden (faktyczna produkcja) wdrożenie.

Dla tej jednej implementacji(możesz wywnioskować i masz rację, że uważam, że mocki do testowania powinny nazywać się Mock(Interfaceename)), wolę nazwę Default (Interfaceename). Jeśli pojawi się bardziej konkretna implementacja, można ją odpowiednio nazwać. Pozwala to również uniknąć sufiksu Impl, którego szczególnie nie lubię (jeśli nie jest to klasa abstrakcyjna, oczywiście jest to "impl"!).

Ja też wolę " Base (Interfaceename)" w przeciwieństwie do "Abstract (Interfaceename)" ponieważ są pewne sytuacje, w których chcesz, aby Twoja klasa bazowa stała się instancyjna później, ale teraz utknąłeś z nazwą " Abstract(Interfaceename)", co zmusza cię do zmiany nazwy klasy, prawdopodobnie powodując małe zamieszanie - ale jeśli zawsze była to Base (Interfaceename), usunięcie modyfikatora abstrakcyjnego nie zmienia tego, czym była klasa.

 87
Author: MetroidFan2002,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2010-05-12 00:48:05

Nazwa interfejsu powinna opisywać abstrakcyjne pojęcie, które reprezentuje interfejs. Każda klasa implementacyjna powinna mieć jakieś specyficzne cechy, które mogą być użyte do nadania jej bardziej konkretnej nazwy.

Jeśli istnieje tylko jedna klasa implementacji i nie możesz wymyślić niczego, co czyni ją specyficzną( sugerując, że chcesz ją nazwać -Impl), to wygląda na to, że nie ma żadnego uzasadnienia, aby mieć interfejs w ogóle.

 57
Author: Michael Borgwardt,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2010-05-11 22:27:12

Mam tendencję do stosowania pseudo-konwencji ustanowionych przez Java Core / Sun, np. w klasach kolekcji:

  • List - interfejs dla obiektu "koncepcyjnego"
  • ArrayList - konkretna implementacja interfejsu
  • LinkedList - konkretna implementacja interfejsu
  • AbstractList - abstrakcyjna" częściowa " implementacja wspomagająca niestandardowe implementacje

Robiłem to samo, modelując moje zajęcia eventowe po paradygmacie AWT Event / Listener / Adapter.

 25
Author: Bert F,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2010-05-11 22:53:48

Standardową konwencją C#, która działa wystarczająco dobrze również w Javie, jest prefiks wszystkich interfejsów z I - więc twój interfejs obsługi plików będzie IFileHandler, A interfejs ciężarówki będzie ITruck. Jest spójny i ułatwia odróżnianie interfejsów od klas.

 18
Author: tzaman,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2010-05-11 22:15:56

Lubię nazwy interfejsów, które wskazują, jaki kontrakt opisuje interfejs, takie jak "porównywalny" lub "Serializowalny". Rzeczowniki takie jak "ciężarówka" tak naprawdę nie opisują ciężarówek - jakie są zdolności Ciężarówki?

Odnośnie konwencji: pracowałem nad projektami, w których każdy interfejs zaczyna się od "I"; choć jest to nieco obce konwencjom Javy, sprawia to, że znajdowanie interfejsów jest bardzo łatwe. Poza tym sufiks "Impl" jest rozsądną domyślną nazwą.

 18
Author: mfx,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2010-05-12 09:55:35

Niektórym się to nie podoba i jest to bardziej konwencja. NET niż Java, ale możesz nazwać swoje interfejsy przedrostkiem capital I, na przykład:

IProductRepository - interface
ProductRepository, SqlProductRepository, etc. - implementations

Ludzie przeciwni tej konwencji nazewnictwa mogą twierdzić, że nie powinno cię to obchodzić, czy pracujesz z interfejsem, czy z obiektem w kodzie, ale uważam, że łatwiej jest go odczytać i zrozumieć w locie.

Nie nazwałbym klasy implementacji przyrostkiem "Class". To może prowadzić do zamieszania, ponieważ można w rzeczywistości pracuj z obiektami "class" (tzn. wpisz) w kodzie, ale w Twoim przypadku nie pracujesz z obiektem class, tylko z zwykłym starym obiektem.

 7
Author: Andy White,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2010-05-11 22:16:45

TruckClass wygląda na to, że była to klasa Truck, myślę, że zalecanym rozwiązaniem jest dodanie przyrostka Impl. Moim zdaniem najlepszym rozwiązaniem jest umieszczenie w nazwie implementacji informacji o tym, co dzieje się w danej implementacji (jak mamy z interfejsem List i implementacjami: ArrayList lub LinkedList), ale czasami mamy tylko jedną implementację i musimy mieć interfejs ze względu na zdalne użycie (na przykład), wtedy (jak wspomniano na początku) Impl jest rozwiązaniem.

 1
Author: Mirek Pluta,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2010-05-11 22:27:50

Używam obu konwencji:

Jeśli interfejs jest specyficzną instancją dobrze znanego wzorca (np. Service, DAO), to może nie być potrzebne "I" (np. UserService, AuditService, UserDao), wszystko działa bez "I", ponieważ po poprawce określa wzorzec meta.

Ale, jeśli masz coś jednorazowego lub podwójnego (Zwykle dla wzorca wywołania zwrotnego), to pomaga odróżnić go od klasy (np. IAsynchCallbackHandler, Iupdatelistener, IComputeDrone). Są to specjalne przeznaczenie interfejsy zaprojektowane do użytku wewnętrznego, czasami interfejs zwraca uwagę na fakt, że operand jest rzeczywiście interfejsem, więc na pierwszy rzut oka jest to natychmiast jasne.

W innych przypadkach można użyć I, aby uniknąć kolizji z innymi powszechnie znanymi klasami betonu(ISubject, IPrincipal vs Subject lub Principal).

 1
Author: Justin,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2010-05-11 23:29:28