Perl Language
Gestion des exceptions
Recherche…
eval et mourir
C'est la manière intégrée de gérer les "exceptions" sans avoir recours à des bibliothèques tierces comme Try :: Tiny .
my $ret;
eval {
$ret = some_function_that_might_die();
1;
} or do {
my $eval_error = $@ || "Zombie error!";
handle_error($eval_error);
};
# use $ret
Nous "abusons" du fait que die
a une valeur de retour fausse, et la valeur de retour du bloc de code global est la valeur de la dernière expression dans le bloc de code:
- si
$ret
est assigné avec succès, alors le1;
expression est la dernière chose qui se produit dans le bloc de codeeval
. Le bloc de codeeval
a donc une valeur vraie, donc le blocor do
ne s'exécute pas. - Si
some_function_that_might_die()
die
, la dernière chose qui se passe dans le bloc de codeeval
est ledie
. Le bloc de codeeval
a donc une valeur fausse et le blocor do
est exécuté. - La première chose que vous devez faire dans le
or do
bloc est lu$@
pour . Cette variable globale contiendra tout argument passé pourdie
. Le|| "Zombie Error"
guard est populaire, mais inutile dans le cas général.
Ceci est important à comprendre car certains appels au dé ne font pas échouer tous les codes, mais la même structure peut être utilisée indépendamment. Considérons une fonction de base de données qui renvoie:
- le nombre de lignes affectées par le succès
-
'0 but true'
si la requête est réussie mais qu'aucune ligne n'a été affectée -
0
si la requête a échoué.
Dans ce cas, vous pouvez toujours utiliser le même idiome, mais vous devez ignorer le dernier 1;
, et cette fonction doit être la dernière chose dans l'éval. Quelque chose comme ça:
eval {
my $value = My::Database::retrieve($my_thing); # dies on fail
$value->set_status("Completed");
$value->set_completed_timestamp(time());
$value->update(); # returns false value on fail
} or do { # handles both the die and the 0 return value
my $eval_error = $@ || "Zombie error!";
handle_error($eval_error);
};
Modified text is an extract of the original Stack Overflow Documentation
Sous licence CC BY-SA 3.0
Non affilié à Stack Overflow