JavaRush /Blog Java /Random-PL /Programowanie obiektowe (tłumaczenie artykułu)
Exidnus
Poziom 38
Санкт-Петербург

Programowanie obiektowe (tłumaczenie artykułu)

Opublikowano w grupie Random-PL
Od tłumacza: Niestety nie mam dużego doświadczenia w tłumaczeniach z języka angielskiego, choć czytam sporo po angielsku. Okazało się jednak, że czytanie i tłumaczenie to dwie różne rzeczy. Niestety nie mam też dużego doświadczenia w programowaniu (ostatnio stworzyłem prostą aplikację internetową w Spring MVC i Hibernate). Dlatego tłumaczenie wyszło znacznie gorzej, niż mogło być. Pozwoliłem sobie nieznacznie poprawić przykłady kodu podane w artykule, ponieważ nie są one zgodne z konwencjami nazewnictwa obowiązującymi w Javie. Być może nie warto było tłumaczyć nazw niektórych wzorców (takie tłumaczenie nie daje zbyt wiele zrozumienia), ale pomyślałem, że to mniejsze zło. Warto osobno wspomnieć o „wysokiej spójności” w tłumaczeniu „wysokiej spójności”. Zgadzam się, nie jest to najlepsze tłumaczenie. Jednak „silna łączność” to „wysokie sprzężenie” (kolejna ważna koncepcja), a „spójność” raczej nie będzie tu odpowiednia. Jestem otwarty na krytykę i z wdzięcznością przyjmę wszelkie uwagi dotyczące artykułu. Programowanie obiektowe to styl programowania, w którym program składa się z komponentów odpowiadających obiektom ze świata rzeczywistego. Każdy rzeczywisty obiekt ma pewne właściwości (które mogą, ale nie muszą zmieniać się w czasie) i zachowanie (które może, ale nie musi) zmieniać się w zależności od innych).warunków). Na przykład ołówek to obiekt ze świata rzeczywistego, który ma następujące właściwości:
  • Jest czerwony (nie zmienia się z biegiem czasu).
  • Ma obecnie 10 centymetrów długości (może się to zmienić, jeśli ołówek zostanie zaostrzony).
I ma następujące zachowanie:
  • Pozostawia ślad, jeśli jest używany prawidłowo.
  • Ślad może się różnić w zależności od ciśnienia (w zależności od czynników zewnętrznych).
  • Jego długość ulega skróceniu w przypadku zaostrzenia (zachowanie trwałe).
Podobnie jak w tym przykładzie, obiekty świata rzeczywistego mogą mieć wiele właściwości, ale pisząc programy bierzemy pod uwagę tylko te niezbędne. Programowanie obiektowe ma swoje zalety. Ułatwia na przykład nawiązanie połączenia pomiędzy obiektem świata rzeczywistego a programem w oczekiwany sposób. To naprawdę pomaga w miarę rozwoju aplikacji i interakcji wielu obiektów ze sobą. Pomaga to w rozłożeniu obowiązków w świecie obiektywnym, pozwalając skupić się na przemyśleniu aplikacji. Kolejną ważną cechą związaną z OOP (programowaniem obiektowym) jest klasyfikacja obiektów. Ponieważ świat (rzeczywisty/wirtualny) jest pełen obiektów, trudno jest sterować nimi indywidualnie. Potrzebujemy sposobu na klasyfikację tych obiektów, który pomoże nam skojarzyć różne obiekty i ich właściwości, na przykład czarny ołówek. Byłby nie do odróżnienia (taki sam?), gdyby został użyty w poprzednim przykładzie, ale jest to inny obiekt. Ale ponieważ oba są ołówkami, należą do tej samej klasy „Ołówek”. Natomiast długopis, który jest bardzo podobny do ołówka, należy do innej klasy. Jednak zarówno pióro, jak i ołówek są „przyborami do pisania”. Programowanie obiektowe opiera się na następujących zasadach:
Abstrakcja
Abstrakcję definiuje się jako jakość interakcji z ideami, a nie zdarzeniami , czyli innymi słowy, wolność od cech reprezentacyjnych . Dzięki temu programiści mogą skupić się na tym, co programować , a nie na tym, jak programować . Abstrakcję można traktować jako umowę, poprzez którą zapewniamy funkcjonalność. Podczas korzystania z tej koncepcji szczegóły implementacji mogą zostać ukryte. Na przykład, jeśli potrzebujemy klasy, która pisze, musimy się upewnić, że ma ona metodę „zapisu”. abstract class writer { write (); } Co zrobiliśmy? Zaprojektowaliśmy klasę wysokiego poziomu, która jest abstrakcyjna, innymi słowy wie, jakiej funkcjonalności potrzebujemy, ale sposób jej zaimplementowania wykracza poza zakres tej klasy. Daje to wiele korzyści:
  • Udostępniamy podmiotom zewnętrznym minimum niezbędnych informacji, co pozwala nam skupić się na przemyśleniu programu (umożliwia to skupione myślenie), uniknąć zamieszania i uniknąć składania niezamierzonych obietnic.
  • Pozostawiamy miejsce na przyszłe ulepszenia, które nie byłyby możliwe, gdyby ujawniono szczegóły wdrożenia.
Dziedzictwo
„Dziedziczenie” w potocznym języku angielskim oznacza „nabywać i przekazywać dalej”. Słowo to istnieje w naszej kulturze od bardzo dawna. Przodkowie zdobyli ziemię ciężką pracą i przekazali ją swoim dzieciom, nawet natura sprzyja dziedziczeniu. Wszystkie właściwości ciała, takie jak wzrost, kolor skóry/oczu/włosów itp. zależy od genów, które odziedziczyliśmy od rodziców. Dziedziczenie zapobiega wymyślaniu koła na nowo i przyspiesza postęp. W OOP jest to samo. Tworzymy klasę nadrzędną z kilkoma podstawowymi właściwościami/zachowaniami. Wszystkie klasy dziedziczące od tego rodzica będą zawierać te same właściwości/zachowania co ich rodzic. Jednak odziedziczone klasy mogą zyskać więcej właściwości/zachowań lub zmienić implementację zachowania. class WritingInstrument { colour; write() { } } class Pen (child of parent) { inkcolour; } W powyższym przykładzie klasa nadrzędna (WritingInstrument) ma właściwość „color” i zachowanie „zapis”. Kiedy zadeklarowana jest klasa potomna (uchwyt), właściwość „color” i zachowanie „zapis” nie muszą być ponownie deklarowane. Występują w klasie „handle” ze względu na dziedziczenie. Jednak klasa potomna może zadeklarować własne dodatkowe właściwości/zachowanie. Jak możemy to wykorzystać w praktyce? My, programiści, jesteśmy bardzo leniwi. Nie chcemy drukować czegoś w kółko. Odradza się istnienie wielu kopii tego samego kodu ze względu na następujące względy:
  • Im mniej kopii kodu, tym łatwiej jest go utrzymać.
  • Jeśli nie ma wielu kopii kodu, zmiana w jednym miejscu będzie widoczna wszędzie.
  • Im mniej kodu, tym mniej błędów.
  • Jeśli jeden kod jest używany w wielu miejscach, osiąga się uogólnienie.
  • Skupiamy się na pisaniu kodu.
  • Skupiamy się na testach.
Dziedziczenie w Javie osiąga się za pomocą słów kluczowych „rozszerza” i „implementuje”. class WritingInstrument { } class Pen extends WritingInstrument { }
Wielopostaciowość
Słowo „polimorfizm” pochodzi od dwóch słów: „poli” , tj. „wiele” / „więcej niż jeden” „morph” , tj. „forma” Dosłownie słowo „polimorfizm” odnosi się do zdolności obiektów do zachowywania się na różne sposoby w zależności od warunków. W programowaniu polimorfizm można wdrożyć w kilku miejscach:
  • Zajęcia
  • Metody
  • Operatorzy
Wszystkie powyższe mogą zachowywać się inaczej w zależności od warunków, być może kontekstu, w którym są używane. Jest to przydatne, ponieważ klient (programista korzystający z Twoich bibliotek) nie musi znać wielu subtelności, a pożądaną funkcjonalność realizuje poprzez wybranie niezbędnych informacji z kontekstu. Class WritingObject { wrire() { // пишем, используя стандартные (по дефолту) цвета } } class Pencil extends WritingObject { write() { // пишем, используя серый цвет, написанный текст можно стереть } } class Pen extends WritingObject { write() { // пишем, используя голубой цвет, написанный текст нельзя стереть } } class Main { main() { WritingObject wr = new WritingObject(); wr.write(); // первый вызов WritingObject wr = new Pen(); wr.write(); // второй вызов WritingObject wr2 = new Pencil(); wr2.write(); // третий вызов } } Powyższy przykład ma domyślną implementację w WritingObject, która jest rozszerzana/zastępowana przez klasy pochodne pen i pen. Metoda write() jest wywoływana trzykrotnie w klasie Main. Za każdym razem wywoływana jest inna implementacja, w zależności od tego, na jakim obiekcie wywoływana jest metoda. W tym przypadku metoda write() ma wiele typów zachowań, ponieważ jest polimorficzna.
Kapsułkowanie
Hermetyzację definiuje się jako gromadzenie powiązanych danych/funkcjonalności w jednej jednostce. Pomaga to w ułatwieniu dostępu do danych/modyfikacji. Przykładowo, jeśli chcemy wydrukować wszystkie właściwości, jakie posiada dany użytkownik, mamy następujące możliwości: printUserProperties(userName, userId, firstname, lastname, email, phone, … … ….) Stworzyliśmy metodę, która pobiera wszystkie właściwości i wypisuje je jedna po drugiej. Wraz ze wzrostem liczby elementów na liście nie będzie już możliwości zidentyfikowania poprawnych pól, a dodanie/usunięcie jednego pola spowoduje zmianę sygnatury metody. Dlatego musimy wymienić wszystkich użytkowników tej metody, nawet jeśli nie potrzebują ostatnio dodanych pól. Aby uczynić kod bardziej czytelnym i ułatwić przyszłe modyfikacje, hermetyzujemy właściwości w klasie i przekształcamy je w obiekt zbiorczy.Obiekt class User { userName userId firstname lastname email phone .. .. .. } printUserProperties(user) {} to pakiet oprogramowania zawierający zmienne i powiązane z nimi metody. Możesz reprezentować obiekty świata rzeczywistego za pomocą obiektów programu. Możesz sobie wyobrazić prawdziwe psy w programie animacyjnym lub prawdziwy rower jako obiekt programowy wewnątrz roweru treningowego. W OOP klasa jest rozszerzalnym szablonem (szablonem kodu programu) służącym do tworzenia obiektów, nadawania im stanu początkowego (zmienne) i implementowania zachowania (funkcje, metody). Akronim SOLID został ukuty przez Michaela Feathera dla określenia „pięciu pierwszych zasad” nazwanych przez Roberta C. Martina na początku XXI wieku. Celem tych zasad, gdy są wdrażane łącznie, jest zwiększenie prawdopodobieństwa, że ​​programista stworzy system łatwy w utrzymaniu i rozbudowie. Zasady SOLID to wytyczne przy tworzeniu programów, które są niezbędne do usunięcia „zgniłego” kodu poprzez refaktoryzację, w wyniku czego kod powinien stać się łatwo czytelny i rozszerzalny. Jest to część zwinnej i adaptacyjnej strategii programowania.
Zasada pojedynczej odpowiedzialności
W OOP zasada pojedynczej odpowiedzialności stanowi, że każda klasa powinna być odpowiedzialna za jedną część funkcjonalności zapewnianej przez program i ta odpowiedzialność powinna być całkowicie zawarta w tej klasie. Cała jego funkcjonalność powinna być ściśle powiązana z tą odpowiedzialnością.
Zasada otwarta/zamknięta
W OOP zasada otwartego/zamkniętego stwierdza, że ​​„jednostki oprogramowania (klasy, moduły, metody itp.) powinny być otwarte na rozszerzenie, ale zamknięte na zmiany”. Innymi słowy, podmiot musi pozwolić na rozszerzenie swojego zachowania bez zmiany kodu źródłowego.
Zasada substytucji Liskowa
Zastępowalność jest zasadą w OOP. Stanowi ona, że ​​jeśli S w programie komputerowym jest podtypem T, to obiekty typu T muszą być takie, aby można je było zastąpić obiektami typu S (czyli obiekty typu S można zastąpić obiektami typu T) bez zmiany wszelkie wymagane programy właściwości (dokładność, realizacja zadań itp.).
Zasada segregacji interfejsów
Zasada separacji interfejsów mówi, że programista-klient nie powinien być zmuszany do polegania na metodach, których nie używa. Zgodnie z tą zasadą konieczne jest podzielenie dużych interfejsów na mniejsze i bardziej szczegółowe, tak aby programista-klient wiedział tylko o tych metodach, które go interesują. Celem zasady oddzielenia interfejsu jest utrzymanie oddzielenia systemu, co ułatwi refaktoryzację, wprowadzanie zmian i ponowne wdrażanie.
Zasada inwersji zależności
W OOP zasada inwersji zależności oznacza specyficzną formę odłączania modułów programu. Kierując się tą zasadą, standardowe relacje zależności ustanowione od modułów wysokiego poziomu tworzących architekturę aplikacji (ustalanie zasad) do zależnych modułów niskiego poziomu zostają odwrócone (odwrócone), tak że zmodyfikowane moduły wysokiego poziomu stają się niezależne od szczegółów implementacji moduły niskiego poziomu. Zasada ta stanowi:
  • Moduły wysokiego poziomu nie powinny zależeć od modułów niskiego poziomu. Obydwa typy modułów muszą zależeć od abstrakcji.
  • Abstrakcje nie powinny zależeć od szczegółów implementacji. Szczegóły muszą zależeć od abstrakcji.
Zasada ta odwraca sposób, w jaki ludzie mogą myśleć o projektowaniu obiektowym, argumentując, że obiekty wysokiego i niskiego poziomu powinny zależeć od tych samych abstrakcji.

zasady GRASP

Wzorce oprogramowania do przypisania ogólnej odpowiedzialności (GRASP) zawierają wytyczne dotyczące przypisywania obowiązków klasom i obiektom w projektowaniu obiektowym.
Kontroler
Wzorzec Controller przypisuje odpowiedzialność za interakcję ze zdarzeniami systemowymi klasom innym niż GUI, które reprezentują cały system lub scenariusz przypadku użycia. Kontroler:
  • Jest to obiekt, który nie wchodzi w bezpośrednią interakcję z użytkownikiem i odpowiada za odbieranie i reagowanie na zdarzenia systemowe.
  • Musi być używany do obsługi wszystkich zdarzeń systemowych jednego (lub wielu powiązanych ze sobą) przypadków użycia.
  • Jest to pierwszy obiekt za GUI, który kontroluje operacje systemu.
  • Nie musi sam wykonywać tej pracy, jego zadaniem jest kontrolowanie biegu wydarzeń.
Twórca
Zadaniem klasy Creator jest tworzenie i inicjowanie obiektów do późniejszego wykorzystania. Zna parametry inicjalizacji, a także jaki obiekt zostanie utworzony. Czasami klasa Creator aktywnie tworzy obiekty i umieszcza je w pamięci podręcznej, a gdy jest to potrzebne, udostępnia jedną instancję.
Wysoka spójność
Wysoka spójność to wzorzec wartościujący, którego celem jest zachowanie obiektów w takim stanie, aby nakierowane były na wykonanie jednego jasnego zadania, były łatwe do kontrolowania i zrozumiałe. Wysokie sprzęgło jest zwykle używane do obsługi niskiego sprzężenia. Wysoka spójność oznacza, że ​​obowiązki danego elementu są jasno określone (silnie powiązane i wysoce skoncentrowane). Podział programu na klasy i podsystemy jest przykładem działań zwiększających spójność właściwości systemu. Luźne powiązanie to natomiast sytuacja, w której element ma zbyt wiele niepowiązanych ze sobą zadań. Luźno powiązane elementy są zwykle trudne do zrozumienia, wielokrotnego użytku, trudne w utrzymaniu i trudne do zmiany.
Pośrednie
Wzorzec Rondo utrzymuje luźne powiązanie (i możliwość ponownego użycia) pomiędzy dwoma elementami poprzez przypisanie odpowiedzialności za interakcję pomiędzy nimi obiektowi pośredniemu. Przykładem jest wprowadzenie kontrolera pośredniczącego pomiędzy danymi (modelem) a ich wyświetlaniem (widokiem) we wzorcu Model-View-Controller (MVC).
Ekspert Informacji
Ekspert informacyjny (również Ekspert lub Zasada Eksperta) to zasada stosowana do określenia, komu przekazać odpowiedzialność. Obowiązki obejmują metody, pola obliczeniowe itp. Przy stosowaniu tej zasady przy przydzielaniu odpowiedzialności głównym podejściem jest następująca sekwencja działań: analiza odpowiedzialności, identyfikacja informacji potrzebnych do jej wypełnienia i wreszcie ustalenie, gdzie te informacje się znajdują. Stosowanie zasady Information Expert powoduje przypisanie odpowiedzialności klasie, która posiada najwięcej informacji, za jej wykonanie.
Niskie sprzęgło
Luźne powiązanie to wzorzec oceny, który określa sposób przypisywania obowiązków: luźne powiązanie między klasami, zmiana jednej powinna mieć minimalny wpływ na drugą, maksymalizując możliwość ponownego użycia.
Wielopostaciowość
Zgodnie z polimorfizmem zmienność zachowania ze względu na typ jest przypisana do typów, w przypadku których występuje ta zmienność. Osiąga się to za pomocą operacji polimorficznych.
Chronione odmiany
Wzorzec Chronionych zmian chroni elementy przed zmianami w innych elementach (obiektach, systemach, podsystemach), skupiając uwagę na niestabilności w interfejsie i wykorzystując polimorfizm do tworzenia różnych implementacji tego interfejsu.
Czysta fabrykacja
Czysta konstrukcja obejmuje klasę, która nie reprezentuje koncepcji w dziedzinie problemu i została zaprojektowana specjalnie w celu osiągnięcia luźnego powiązania, wysokiej spójności, a tym samym maksymalnego potencjału ponownego wykorzystania (rozwiązanie oferowane przez wzorzec Information Expert tego nie osiąga). Taka klasa jest zwykle nazywana „usługą” w projektowaniu opartym na domenie.

Krytyka

Badania Potoka i wsp. nie wykazały znaczących różnic pomiędzy podejściem OOP a podejściem proceduralnym.
Krytyczne porównanie OOP z innymi technologiami, zwłaszcza relacyjnymi, jest trudne ze względu na brak rygorystycznej i powszechnie akceptowanej definicji OOP (Christopher J. Date).
W porównaniu do innych języków (dialekty LISP, języki funkcjonalne itp.) języki OOP nie mają wyjątkowej przewagi i nie narzucają niepotrzebnej złożoności. (Lawrence Krubner)
Uważam, że programowanie obiektowe jest technicznie słabe. Próbuje rozłożyć świat na części pod względem interfejsów różniących się w ramach jednego typu. Aby poradzić sobie z prawdziwymi problemami, potrzebujesz wielosortowych algebr – rodzin interfejsów obejmujących wiele typów. Uważam programowanie obiektowe za filozoficznie niezdrowe. Stwierdza, że ​​wszystko jest przedmiotem. Nawet jeśli to prawda, nie jest to zbyt interesujące: powiedzieć, że wszystko jest przedmiotem, to nie powiedzieć nic. (Aleksander Stiepanow)
Popularność OOP wśród dużych firm wynika z „dużych (i często zmieniających się) grup przeciętnych programistów”. Dyscyplina narzucona przez OOP zapobiega wyrządzeniu przez programistę „zbyt dużej szkody”. (Paul Graham)
Programowanie obiektowe stawia rzeczowniki na pierwszym miejscu. Po co sięgać po tak ekstremalne środki i wynieść jedną część mowy na piedestał? Dlaczego jedna koncepcja ma pierwszeństwo przed inną? Nie jest możliwe, aby OOP nagle uczynił czasowniki mniej ważnymi dla naszego myślenia. To dziwnie wypaczona perspektywa. (Steve Yegge)
Rick Hickey, twórca Clojure, opisał systemy obiektowe jako niezwykle uproszczone modele świata rzeczywistego. Podkreślił niezdolność OOP do prawidłowego modelowania czasu, co stwarza ogromne problemy, gdy wielowątkowość staje się powszechna w programach. Eric S. Raymond, programista uniksowy i zwolennik oprogramowania open source, krytycznie odniósł się do twierdzenia, że ​​OOP to „jedyne rozwiązanie” i napisał, że OOP zachęca do tworzenia programów wielowarstwowych, co utrudnia przejrzystość. Jako podejście odwrotne Raymond podał przykład Uniksa i C.

Spinki do mankietów

Autor: Margaret Rouse z Wikipedii WhatIs.com! ( wersja rosyjska ) dziedziczenie to polimorfizm SOLID (projektowanie obiektowe) ( wersja rosyjska ) Zasada pojedynczej odpowiedzialnościArgumenty przeciwko OOPS ( wersja rosyjska ) Czym jest OOPS (bez szumu) Tłumaczenie: Varygin D.V.
Komentarze
TO VIEW ALL COMMENTS OR TO MAKE A COMMENT,
GO TO FULL VERSION