Erlang - Ausnahmen

In jeder Programmiersprache ist eine Ausnahmebehandlung erforderlich, um die Laufzeitfehler zu behandeln, damit der normale Ablauf der Anwendung aufrechterhalten werden kann. Eine Ausnahme stört normalerweise den normalen Ablauf der Anwendung. Aus diesem Grund müssen wir in unserer Anwendung die Ausnahmebehandlung verwenden.

Wenn in Erlang eine Ausnahme oder ein Fehler auftritt, wird normalerweise die folgende Meldung angezeigt.

{"init terminating in do_boot", {undef,[{helloworld,start,[],[]}, 
{init,start_it,1,[]},{init,start_em,1,[]}]}}

Crash Dump wird geschrieben an -

erl_crash.dump
init terminating in do_boot ()

In Erlang gibt es drei Arten von Ausnahmen:

  • Error - Anrufen erlang:error(Reason)beendet die Ausführung im aktuellen Prozess und enthält eine Stapelverfolgung der zuletzt aufgerufenen Funktionen mit ihren Argumenten, wenn Sie sie abfangen. Dies sind die Ausnahmen, die die oben genannten Laufzeitfehler hervorrufen.

  • Exists- Es gibt zwei Arten von Ausgängen: "interne" Ausgänge und "externe" Ausgänge. Die internen Exits werden durch Aufrufen der Funktion ausgelöstexit/1und lassen Sie den aktuellen Prozess seine Ausführung stoppen. Die externen Ausgänge werden mit aufgerufenexit/2 und haben mit mehreren Prozessen im gleichzeitigen Aspekt von Erlang zu tun.

  • Throw- Ein Wurf ist eine Ausnahmeklasse, die für Fälle verwendet wird, die vom Programmierer erwartet werden. Im Vergleich zu Exits und Fehlern führen sie keinen "Absturz dieses Prozesses" durch! Absicht hinter ihnen, sondern sie kontrollieren den Fluss. Da Sie Würfe verwenden, während Sie erwarten, dass der Programmierer sie verarbeitet, ist es normalerweise eine gute Idee, ihre Verwendung innerhalb eines Moduls zu dokumentieren, das sie verwendet.

EIN try ... catch Auf diese Weise können Sie einen Ausdruck auswerten und gleichzeitig den erfolgreichen Fall sowie die aufgetretenen Fehler behandeln.

Die allgemeine Syntax eines try catch-Ausdrucks lautet wie folgt.

Syntax

try Expression of 
SuccessfulPattern1 [Guards] -> 
Expression1; 
SuccessfulPattern2 [Guards] -> 
Expression2 

catch 
TypeOfError:ExceptionPattern1 -> 
Expression3; 
TypeOfError:ExceptionPattern2 -> 
Expression4 
end

Der Ausdruck dazwischen try and ofsoll geschützt sein. Dies bedeutet, dass jede Art von Ausnahme, die innerhalb dieses Anrufs auftritt, abgefangen wird. Die Muster und Ausdrücke zwischen dentry ... of and catch verhalten sich genauso wie a case ... of.

Zum Schluss das Fangteil - hier können Sie ersetzen TypeOfErrorentweder durch Fehler, Werfen oder Beenden für jeden Typ, den wir in diesem Kapitel gesehen haben. Wenn kein Typ angegeben ist, wird ein Wurf angenommen.

Im Folgenden sind einige der Fehler und die Fehlergründe in Erlang aufgeführt:

Error Art des Fehlers
Badarg Schlechtes Argument. Das Argument hat einen falschen Datentyp oder ist auf andere Weise schlecht geformt.
Badarith Schlechtes Argument in einem arithmetischen Ausdruck.
{Badmatch, V} Die Auswertung eines Übereinstimmungsausdrucks ist fehlgeschlagen. Der Wert V stimmte nicht überein.
Funktionsklausel Bei der Auswertung eines Funktionsaufrufs wird keine übereinstimmende Funktionsklausel gefunden.
{case_clause, V} Bei der Auswertung eines Fallausdrucks wird kein passender Zweig gefunden. Der Wert V stimmte nicht überein.
if_clause Bei der Auswertung eines if-Ausdrucks wird kein wahrer Zweig gefunden.
{try_clause, V} Bei der Auswertung des of-Abschnitts eines try-Ausdrucks wird kein passender Zweig gefunden. Der Wert V stimmte nicht überein.
undef Die Funktion kann bei der Auswertung eines Funktionsaufrufs nicht gefunden werden.
{badfun, F} Mit einem lustigen F stimmt etwas nicht
{Badarität, F} Ein Spaß wird auf die falsche Anzahl von Argumenten angewendet. F beschreibt den Spaß und die Argumente.
timeout_value Der Timeout-Wert in einem Ausdruck "receive..after" wird zu etwas anderem als einer Ganzzahl oder Unendlichkeit ausgewertet.
noproc Es wird versucht, eine Verknüpfung zu einem nicht vorhandenen Prozess herzustellen.

Das Folgende ist ein Beispiel dafür, wie diese Ausnahmen verwendet werden können und wie Dinge getan werden.

  • Die erste Funktion generiert alle möglichen Arten einer Ausnahme.

  • Dann schreiben wir eine Wrapper-Funktion zum Aufrufen generate_exception in einem Versuch ... Ausdruck fangen.

Beispiel

-module(helloworld). 
-compile(export_all). 

generate_exception(1) -> a; 
generate_exception(2) -> throw(a); 
generate_exception(3) -> exit(a); 
generate_exception(4) -> {'EXIT', a}; 
generate_exception(5) -> erlang:error(a). 

demo1() -> 
   [catcher(I) || I <- [1,2,3,4,5]]. 
catcher(N) -> 
   try generate_exception(N) of 
      Val -> {N, normal, Val} 
   catch 
      throw:X -> {N, caught, thrown, X}; 
      exit:X -> {N, caught, exited, X}; 
      error:X -> {N, caught, error, X} 
   end. 
      
demo2() -> 
   [{I, (catch generate_exception(I))} || I <- [1,2,3,4,5]]. 
demo3() -> 
   try generate_exception(5) 
   catch 
      error:X -> 
         {X, erlang:get_stacktrace()} 
   end. 
   
lookup(N) -> 
   case(N) of 
      1 -> {'EXIT', a}; 
      2 -> exit(a) 
   end.

Wenn wir das Programm als helloworld ausführen: demo (). erhalten wir die folgende Ausgabe -

Ausgabe

[{1,normal,a},
{2,caught,thrown,a},
{3,caught,exited,a},
{4,normal,{'EXIT',a}},
{5,caught,error,a}]