F # - Manejo de excepciones

Una excepción es un problema que surge durante la ejecución de un programa. Una excepción F # es una respuesta a una circunstancia excepcional que surge mientras se ejecuta un programa, como un intento de dividir por cero.

Las excepciones proporcionan una forma de transferir el control de una parte de un programa a otra. El manejo de excepciones de F # proporciona las siguientes construcciones:

Construir Descripción
subir expr Genera la excepción dada.
falla con expr Eleva el System.Exception excepción.
prueba expr con reglas Captura expresiones que coinciden con las reglas del patrón.
intente expr finalmente expr Ejecución del finally expresión tanto cuando el cálculo es exitoso como cuando se genera una excepción.
| :? ArgumentException Una regla que coincide con el tipo de excepción de .NET dado.
| :? ArgumentException como e Una regla que coincide con el tipo de excepción de .NET dado, vinculando el nombre e al valor del objeto de excepción.
| Fallo (msg) → expr Una regla que coincide con la excepción de F # que transporta datos.
| exn → expr Una regla que coincide con cualquier excepción, vinculando el nombre exn al valor del objeto de excepción.
| exn cuando expr → expr Una regla que coincide con la excepción bajo la condición dada, vinculando el nombre exn al valor del objeto de excepción.

Comencemos con la sintaxis básica del manejo de excepciones.

Sintaxis

La sintaxis básica para el bloque de manejo de excepciones de F # es -

exception exception-type of argument-type

Dónde,

  • exception-type es el nombre de un nuevo tipo de excepción de F #.

  • argument-type representa el tipo de argumento que se puede suministrar cuando genera una excepción de este tipo.

  • Se pueden especificar varios argumentos utilizando un tipo de tupla para el tipo de argumento.

los try...with La expresión se usa para el manejo de excepciones en el lenguaje F #.

La sintaxis para probar ... con expresión es -

try
   expression1
with
   | pattern1 -> expression2
   | pattern2 -> expression3
...

los try...finally La expresión le permite ejecutar código de limpieza incluso si un bloque de código arroja una excepción.

Sintaxis para probar ... finalmente la expresión es -

try
   expression1
finally
   expression2

los raiseLa función se utiliza para indicar que se ha producido un error o una condición excepcional. También captura la información sobre el error en un objeto de excepción.

La sintaxis de la función de aumento es:

raise (expression)

los failwith La función genera una excepción de F #.

La sintaxis de la función failwith es -

failwith error-message-string

los invalidArg La función genera una excepción de argumento.

invalidArg parameter-name error-message-string

Ejemplo de manejo de excepciones

Ejemplo 1

El siguiente programa muestra el manejo básico de excepciones con un simple intento ... con bloque -

let divisionprog x y =
   try
      Some (x / y)
   with
      | :? System.DivideByZeroException -> printfn "Division by zero!"; None

let result1 = divisionprog 100 0

Cuando compila y ejecuta el programa, produce el siguiente resultado:

Division by zero!

Ejemplo 2

F # proporciona una exceptiontipo para declarar excepciones. Puede utilizar un tipo de excepción directamente en los filtros en untry...with expresión.

El siguiente ejemplo demuestra esto:

exception Error1 of string
// Using a tuple type as the argument type.
exception Error2 of string * int

let myfunction x y =
   try
      if x = y then raise (Error1("Equal Number Error"))
      else raise (Error2("Error Not detected", 100))
   with
      | Error1(str) -> printfn "Error1 %s" str
      | Error2(str, i) -> printfn "Error2 %s %d" str i
myfunction 20 10
myfunction 5 5

Cuando compila y ejecuta el programa, produce el siguiente resultado:

Error2 Error Not detected 100
Error1 Equal Number Error

Ejemplo 3

El siguiente ejemplo demuestra el manejo de excepciones anidadas:

exception InnerError of string
exception OuterError of string

let func1 x y =
   try
      try
         if x = y then raise (InnerError("inner error"))
         else raise (OuterError("outer error"))
      with
         | InnerError(str) -> printfn "Error:%s" str
   finally
      printfn "From the finally block."

let func2 x y =
   try
      func1 x y
   with
      | OuterError(str) -> printfn "Error: %s" str

func2 100 150
func2 100 100
func2 100 120

Cuando compila y ejecuta el programa, produce el siguiente resultado:

From the finally block.
Error: outer error
Error:inner error
From the finally block.
From the finally block.
Error: outer error

Ejemplo 4

La siguiente función demuestra la failwith función -

let divisionFunc x y =
   if (y = 0) then failwith "Divisor cannot be zero."
   else
      x / y

let trydivisionFunc x y =
   try
      divisionFunc x y
   with
      | Failure(msg) -> printfn "%s" msg; 0

let result1 = trydivisionFunc 100 0
let result2 = trydivisionFunc 100 4
printfn "%A" result1
printfn "%A" result2

Cuando compila y ejecuta el programa, produce el siguiente resultado:

Divisor cannot be zero.
0
25

Ejemplo 5

los invalidArgLa función genera una excepción de argumento. El siguiente programa demuestra esto:

let days = [| "Sunday"; "Monday"; "Tuesday"; "Wednesday"; "Thursday"; "Friday"; "Saturday" |]
let findDay day =
   if (day > 7 || day < 1)
      then invalidArg "day" (sprintf "You have entered %d." day)
   days.[day - 1]

printfn "%s" (findDay 1)
printfn "%s" (findDay 5)
printfn "%s" (findDay 9)

Cuando compila y ejecuta el programa, produce el siguiente resultado:

Sunday
Thursday
Unhandled Exception:
System.ArgumentException: You have entered 9.
…

También se mostrará alguna otra información sobre el archivo y la variable que causan el error en el sistema, según el sistema.