Try, Catch, Finally
Część sekcji Programowanie obiektowe ścieżki PHP w Coddy. Lekcja 68 z 91.
Teraz, gdy wiesz, jak tworzyć i zgłaszać wyjątki, musisz nauczyć się je przechwytywać. Struktura try-catch-finally pozwala elegancko obsługiwać wyjątki, zamiast pozwalać im powodować awarię aplikacji.
Umieść kod, który może zgłosić wyjątek, w bloku try, a następnie obsłuż wyjątek w bloku catch:
<?php
class Calculator {
public function divide(int $a, int $b): float {
if ($b === 0) {
throw new InvalidArgumentException("Cannot divide by zero");
}
return $a / $b;
}
}
$calc = new Calculator();
try {
echo $calc->divide(10, 0);
} catch (InvalidArgumentException $e) {
echo "Error: " . $e->getMessage();
}
Wynik:
Error: Cannot divide by zeroMożesz przechwytywać różne typy wyjątków za pomocą wielu bloków catch. PHP sprawdza je po kolei, dlatego umieszczaj bardziej szczegółowe wyjątki wcześniej:
<?php
try {
// ryzykowny kod
} catch (InvalidArgumentException $e) {
echo "Bad input: " . $e->getMessage();
} catch (Exception $e) {
echo "Something went wrong: " . $e->getMessage();
}
Blok finally wykonuje się niezależnie od tego, czy wyjątek został zgłoszony lub przechwycony. Doskonale nadaje się do zadań porządkowych, takich jak zamykanie połączeń:
<?php
try {
echo "Attempting operation\n";
throw new Exception("Failed");
} catch (Exception $e) {
echo "Caught: " . $e->getMessage() . "\n";
} finally {
echo "Cleanup complete";
}
Wynik:
Attempting operation
Caught: Failed
Cleanup completeBlok finally wykonuje się nawet wtedy, gdy zwrócisz wartość z bloku try lub catch, dzięki czemu można na nim polegać przy niezbędnych operacjach porządkowych.
Wyzwanie
ŁatwyZbudujmy system przetwarzania plików, który pokazuje, jak try-catch-finally współpracują przy sprawnej obsłudze błędów i zapewnianiu, że czyszczenie zawsze zostanie wykonane.
Podzielisz kod na trzy pliki:
FileException.php: Utwórz własną klasęFileException, która rozszerzaException. Będzie ona reprezentować błędy związane z plikami w twoim systemie.FileProcessor.php: Utwórz klasęFileProcessor, która symuluje operacje na plikach. Dołącz plik FileException. Twoja klasa powinna zawierać:- Prywatną właściwość logiczną
$isOpen, zainicjalizowaną wartościąfalse - Metodę
open(string $filename): void, która ustawia$isOpennatruei wyświetla"Opening: [filename]". Jeśli nazwa pliku to"invalid.txt", rzuć wyjątekFileExceptionz komunikatem"Cannot open file" - Metodę
process(): void, która wyświetla"Processing file...". Jeśli$isOpenma wartośćfalse, rzuć wyjątekRuntimeExceptionz komunikatem"File not open" - Metodę
close(): void, która ustawia$isOpennafalsei wyświetla"File closed" - Metodę
isOpen(): bool, która zwraca bieżący stan
- Prywatną właściwość logiczną
main.php: Dołącz plik FileProcessor. Otrzymasz jedno wejście: nazwę pliku.Utwórz obiekt
FileProcessori użyj strukturytry-catch-finally, aby:- W bloku
try: wywołaćopen()z nazwą pliku, a następnie wywołaćprocess() - Najpierw przechwycić
FileExceptioni wyświetlić"File error: [message]" - Przechwycić
RuntimeExceptioni wyświetlić"Runtime error: [message]" - W bloku
finally: sprawdzić za pomocąisOpen(), czy plik jest otwarty, a jeśli tak, wywołaćclose(). Następnie wyświetlić"Cleanup complete"
- W bloku
Blok finally zapewnia wykonanie czyszczenia niezależnie od tego, czy operacje się powiodą, czy nie. Ten wzorzec jest niezbędny do zarządzania zasobami, takimi jak pliki, połączenia z bazą danych czy gniazda sieciowe, w przypadku których czyszczenie musi nastąpić niezależnie od tego, co wydarzy się podczas przetwarzania.
Spróbuj swoich sił
<?php
require_once 'FileProcessor.php';
// Odczytaj dane wejściowe
$filename = trim(fgets(STDIN));
// TODO: Utwórz instancję FileProcessor
// TODO: Użyj struktury try-catch-finally:
// - W bloku try: wywołaj open() z nazwą pliku, a następnie wywołaj process()
// - Najpierw przechwyć FileException i wypisz "File error: [message]"
// - Przechwyć RuntimeException i wypisz "Runtime error: [message]"
// - W bloku finally: sprawdź za pomocą isOpen(), czy plik jest otwarty; jeśli tak, wywołaj close()
// Następnie wypisz "Cleanup complete"
?>Ta lekcja zawiera krótki quiz. Zacznij lekcję, żeby na niego odpowiedzieć i śledzić swoje postępy.
Wszystkie lekcje w sekcji Programowanie obiektowe
1Podstawy programowania obiektowego
Pliki zewnętrzneWprowadzenie do programowania obiektowegoKlasy a obiektySłowo kluczowe $thisMetodyWłaściwościKonstruktor (__construct)Destruktor (__destruct)Powtórka — prosty kalkulator4Dziedziczenie
Podstawy dziedziczeniaSłowo kluczowe parent::Przesłanianie metodSłowo kluczowe finalKlasy abstrakcyjnePowtórzenie – hierarchia pracowników7Enkapsulacja
Public, protected, privateModyfikatory dostępu w szczegółachGettery i setteryUkrywanie informacjiPromocja parametrów konstruktora (8.0)Podsumowanie — system ewidencji studentów2Przestrzenie nazw i autoloading
Wprowadzenie do przestrzeni nazwSłowo kluczowe useStandard autoloadingu PSR-4Autoloader ComposeraPodsumowanie – uporządkowany projekt5Interfejsy i kontrakty
Wprowadzenie do interfejsówImplementowanie interfejsówImplementowanie wielu interfejsówInterfejs a klasa abstrakcyjnaPodpowiadanie typów za pomocą interfejsówPodsumowanie — kalkulator kształtów8Metody magiczne
Wprowadzenie do metod magicznych__toString i __debugInfo__get, __set, __isset, __unset__call i __callStatic__clone i klonowanie obiektów__serialize i __unserializePodsumowanie — własna kolekcja11System typów i obsługa błędów
Deklaracje typówTypy nullableTypy sumy i przecięciaKlasy wyjątkówNiestandardowa hierarchia wyjątkówTry, Catch, FinallyPodsumowanie — walidator formularzy14Projekt: Zarządzanie biblioteką
Przegląd projektuKlasy książki i użytkownika3Właściwości klas
Właściwości instancji a właściwości statyczneStałe w klasachMetody i właściwości statyczneWłaściwości prywatne i chronioneWłaściwości tylko do odczytu (PHP 8.1)Podsumowanie — menedżer kont bankowych6Polimorfizm
Ponowne omówienie nadpisywania metodPolimorfizm za pomocą interfejsówPodpowiedzi typów i typy sumyPóźne wiązanie statycznePodsumowanie — procesor płatności9Cechy
Wprowadzenie do cechKorzystanie z wielu cechRozwiązywanie konfliktów cechMetody abstrakcyjne w cechachCechy a dziedziczenie12Wzorce projektowe, część 1
Wprowadzenie do wzorców projektowychWzorzec SingletonWzorzec FactoryWzorzec ObserverWzorzec StrategyPoćwicz samodzielnie: Kompilator PHP online