Po przeczytaniu wczoraj postu zdałem sobie sprawę, że niewiele wiem o pochodzeniu wyjątków. Czy to tylko koncepcja związana z OOP? Myślę, że tak, ale znowu są wyjątki od bazy danych.
programming-languages
exceptions
John V.
źródło
źródło
goto
. W szczególności cel rzut zależy od kontekstu, opartego na zagnieżdżeniu struktur blokowych. Jako takie wyjątki są nawet zależne od nieco mniej ścisłej formy programowania strukturalnego, w której zasada pojedynczego wyjścia jest traktowana jako wytyczna, ale nie absolut ”.Odpowiedzi:
Wyjątki nie są koncepcją OOP.
Ale nie są one całkowicie niezwiązane ani w jednym małym maleńkim punkcie.
Jak pokazały inne odpowiedzi: koncepcja wyjątków pojawiła się w kilku językach innych niż OOP. Nic w tej koncepcji nie wymaga czegoś od OOP.
Ale wszelkie, jeśli nie wszystkie języki OOP, które traktują OOP poważnie, wymagają wyjątków, ponieważ inne metody obsługi błędów zawodzą w jednym konkretnym punkcie: Konstruktor.
Jednym z punktów OOP jest to, że obiekt hermetyzuje i całkowicie zarządza swoim stanem wewnętrznym. Oznacza to również, że w czystym OOP potrzebujesz koncepcji stworzenia nowego obiektu ze spójnym stanem „atomowo” - wszystko, od alokacji pamięci (jeśli jest wymagana) do inicjalizacji do znaczącego stanu (tj. Proste zerowanie pamięci nie wystarczy) zrobić to w jednym wyrażeniu. Dlatego wymagany jest konstruktor :
Ale to oznacza, że konstruktor może również zawieść z powodu błędu. Jak propagować informacje o błędzie z konstruktora bez wyjątków?
Zwracana wartość? Zawodzi, ponieważ w niektórych językach
new
może zwrócić tylko,null
ale nie ma żadnych istotnych informacji. W innych językach (np. C ++)myFoo
nie jest wskaźnikiem. Nie można tego sprawdzićnull
. Nie możesz też zapytaćmyFoo
o błąd - nie jest on inicjowany, a zatem „nie istnieje” w myśleniu OOP.Globalna flaga błędu? Tyle o kapsułkowaniu stanu, a potem jakiejś zmiennej globalnej? Idź do h ... ;-)
Mikstura? W żadnym wypadku nie lepiej.
?
Tak więc wyjątki są bardziej fundamentalną koncepcją niż OOP, ale OOP opiera się na nich w naturalny sposób.
źródło
Nie. Wyjątki i OOP nie są ze sobą powiązane.
Obsługa wyjątków jest mechanizmem obsługi błędów. Wyjątek jest obsługiwany przez zapisanie bieżącego stanu wykonania w predefiniowanym miejscu i przełączenie wykonania na określony podprogram znany jako moduł obsługi wyjątków.
Porównując C ( niezupełnie język OOP , możliwe w jakiś sposób emulować wyjątki w C ) i C ++ (OOP, obsługuje wyjątki), nic nie stoi na przeszkodzie, aby standardowa komisja C dodawała obsługę wyjątków do C, nadal nie uczyni z C języka OOP.
źródło
ON ERROR GOTO xxxx
try catch
konstrukcji.Wyjątkiem jest, mówiąc wprost, wyjątkowa sytuacja wymagająca uwagi i często zmiany w przebiegu wykonywania programu. Zgodnie z tą definicją wyjątki i obsługa wyjątków nie ograniczają się do orientacji obiektowej, a proste błędy programu można uznać za formę wyjątku.
Języki zorientowane obiektowo zazwyczaj mają natywną klasę wyjątków, a w zależności od kontekstu słowo „wyjątek” może rzeczywiście odnosić się do tej klasy natywnej zamiast ogólnej koncepcji. Obsługa wyjątków zorientowanych obiektowo jest, jak większość zorientowana obiektowo, cukrem syntaktycznym i może być łatwo emulowana w zdecydowanie nie zorientowanych obiektowo językach. Oto przykład C z wikibooka Programowanie C :
źródło
Odpowiedź jest prosta NIE.
Dobrym przykładem języka innego niż OO z wyjątkami jest ADA.
źródło
Kilka bardzo dobrych odpowiedzi już tutaj. Inne przykłady języków programowania innych niż OOP z wyjątkami:
Oracle PL / SQL
klasyczny Visual Basic (wersja 6 i niższa, „On Error Goto” to IMHO forma obsługi wyjątków)
(Szczerze mówiąc: w niektórych językach można znaleźć elementy OO, ale chyba mechanika obsługi wyjątków ich nie używa, ponieważ koncepcja została wprowadzona wiele lat przed dodaniem elementów OO do tych języków).
źródło
ON ERROR GOTO
składni. Nawet QuickBASIC miał kilka koncepcji podobnych do OO (myślę, że QB 4.5 nawet wspierał jakieś klasy), ale trudno byłoby nazwać w większości tradycyjny BASIC właściwym językiem zorientowanym obiektowo. [Wikipedia ]Podstawową ideą wyjątków jest oczyszczenie przepływu programu, aby programiści mogli łatwiej podążać „normalną” ścieżką wykonania. Rozważ prosty przypadek otwarcia pliku w C. Natychmiast po próbie otwarcia pliku programista musi zbadać odpowiedź wywołania fopen () i zdecydować, czy wywołanie się powiodło. Jeśli wywołanie nie powiedzie się, programista musi odpowiednio odpowiedzieć. Następne wywołanie w „normalnej” ścieżce wykonania, być może wywołanie fread () lub fwrite (), pojawi się po obsłużeniu warunków błędu lub niepowodzenia. To może być na następnym ekranie.
W języku, który zapewnia wyjątki, po równoważnym wywołaniu fopen () może natychmiast następować fread () lub fwrite (). Nie ma obsługi błędów, które ukrywają „następny krok” „normalnej” ścieżki wykonania. Programista może zobaczyć więcej normalnej ścieżki na jednym ekranie, dzięki czemu może łatwiej śledzić wykonanie. Obsługa błędów jest przenoszona do innej części programu.
Same wyjątki nie są koncepcją OOP, ale często są wdrażane przy użyciu koncepcji OOP, dzięki czemu są wygodniejsze i wydajniejsze. Na przykład wyjątki można zdefiniować za pomocą hierarchii dziedziczenia. Korzystając z naszego hipotetycznego przykładu otwierania, odczytu lub zapisu pliku, każde z tych wywołań może generować różne wyjątki - FileClosedException, DeviceFullException, NoSuchFileException, InsufficientFilePermissionsException itp. Każdy z nich może dziedziczyć po FileException, który może odziedziczyć po IOException, który może Dziedzicz z GenericException.
Jeśli programista wykonuje szybką i nieprzyzwoitą implementację w celu przetestowania koncepcji, może w większości zignorować obsługę wyjątków i po prostu zaimplementować pojedynczy moduł obsługi dla GenericException. Ten moduł obsługi będzie obsługiwał GenericException i każdy wyjątek, który dziedziczy z GenericException. Jeśli chce traktować dowolny wyjątek związany z plikiem w ten sam sposób, może napisać moduł obsługi wyjątku FileException. Będzie to wywoływane w przypadku wyjątków FileException i wszelkich wyjątków dziedziczących po FileException. Jeśli chce napisać program, który będzie różnie reagował na różne warunki błędu, może napisać określoną procedurę obsługi dla każdego konkretnego wyjątku.
źródło
Inni słusznie odpowiedzieli „Nie” z przykładami języków. Pomyślałem, że mogę rozszerzyć, dodając przykład dodawania wyjątków do języka bez angażowania OOP.
Zrobię to w przypadku DSKL (deklaratywnego języka sekwencyjnego jądra) OZ , języka dobrze przystosowanego do tego rodzaju zajęć akademickich. DSKL (lub DKL) można zobaczyć tutaj (losowy wynik wyszukiwania), część Oświadczenia i wartości. Dokładna definicja nie jest ważna, poza tym, że jest to bardzo prosty język bez zmiennych, które można modyfikować (są zadeklarowane i później powiązane), i nie ma wbudowanego OOP.
Nie można nawet dodać OOP jako abstrakcji językowej do tego języka jądra. Dodając unikalne nazwy do języka jądra (NewName) i używając lokalnego zakresu, można uzyskać enkapsulację. Lub dodając zmienny stan do języka jądra (NewCell) i używając lokalnego zakresu można uzyskać właściwe OOP z enkapsulacją. Ale nie można tego osiągnąć tylko z określonym językiem jądra.
Jeśli następnie dodamy wyjątki do języka jądra, będziemy mieli język bez obsługi OOP, ale z wyjątkami. Pokażę jak:
Definiując maszynę abstrakcyjną ze stosem i pamięcią, możemy zdefiniować, co powinna zrobić każda instrukcja w naszym języku ( semantyka instrukcji). Na przykład
skip
w stosie nie należy nic robić,A = 3
w stosie należy powiązać (/ ujednolicić) A z (/ with) 3.Zaczynamy od dodania składni sposobu definiowania naszych wyjątków. Robimy to, dodając kolejne dwie klauzule do
<statement>
DKL.Oto znany try / catch i sposób na zgłaszanie wyjątków.
Ich semantykę definiujemy według tego, jak powinny działać na maszynie abstrakcyjnej:
Spróbuj
Oświadczenie semantyczne brzmi:
(try <statement1> catch <id> then <statement2> end)
Wykonaj:
(catch <id> then <statement2> end)
(<statement1>)
Zauważ, że instrukcja 1 będzie na górze stosu i najpierw zostanie wykonana.
Raise
Stwierdzenie semantyczne brzmi:
(raise <id> end)
Do:
(catch <id> then <statement> end)
Push
(<statement>)
na stosie.Catch
Jeśli podczas normalnego wykonywania widzimy instrukcję catch, oznacza to, że wszystko, co było w środku, zostało wykonane bez podniesienia wyjątków do tego poziomu. W ten sposób po prostu otwieramy
catch
stos i nic nie robimy.QED, mamy język z wyjątkami i brak możliwości OOP.
Usunąłem część środowiska z abstrakcyjnej maszyny, aby była prostsza.
źródło
Nie.
IIRC, wyjątki pojawiły się przed pierwszymi językami OO. AFAIK, wyjątki były najpierw wspierane przez wczesne wdrożenia LISP. Języki wczesnej struktury (np. ALGOL) i wczesne języki OO (np. SIMULA) nie obsługiwały wyjątków.
źródło