42

me gustaría lanzar una excepción y tienen la siguiente:¿Cómo puedo lanzar una excepción en Clojure?

(throw "Some text") 

Sin embargo, parece ser ignorado.

+2

'throw' lanza instancias de Java' Throwable'. Does '(throw (Exception." Some text "))' work? – dfan

+0

cuando intento (tiro "Some text") obtengo una ClassClassException porque String no se puede convertir a Throwable. Entonces es extraño que el tiro esté siendo "ignorado" en su caso ... – mikera

Respuesta

68

Usted necesita para envolver la cadena en un Throwable:

(throw (Throwable. "Some text")) 

o

(throw (Exception. "Some text")) 

Puede configurar un try/catch/bloque finally así:

(defn myDivision [x y] 
    (try 
    (/ x y) 
    (catch ArithmeticException e 
     (println "Exception message: " (.getMessage e))) 
    (finally 
     (println "Done.")))) 

REPL sesión:

user=> (myDivision 4 2) 
Done. 
2 
user=> (myDivision 4 0) 
Exception message: Divide by zero 
Done. 
nil 
+0

Brillante respuesta. ¡Gracias! – Zubair

8

clojure.contrib.condition proporciona un medio amigable Clojure para manejar excepciones. Puedes plantear condiciones con causas. Cada condición puede tener su propio controlador.

Hay un número de ejemplos en el source on github.

Es bastante flexible, ya que puede proporcionar su propia clave, pares de valores al aumentar y luego decidir qué hacer en su controlador en función de las claves/valores.

E.g. (Mangling el código de ejemplo):

(if (something-wrong x) 
    (raise :type :something-is-wrong :arg 'x :value x)) 

, entonces puede tener un controlador para :something-is-wrong:

(handler-case :type 
    (do-non-error-condition-stuff) 
    (handle :something-is-wrong 
    (print-stack-trace *condition*))) 
+4

Ahora se reemplaza por [slingshot] (https://github.com/scgilardi/slingshot) (tomado de [Where Did Clojure.Contrib Go] (http: //dev.clojure.org/display/design/Where + Did + Clojure.Contrib + Go)) – kolen

7

Si desea lanzar una excepción e incluir información de depuración en él (además de un mensaje cadena), puede usar la función incorporada ex-info.

Para extraer los datos del objeto ex-info previamente construido, use ex-data.

Ejemplo de clojuredocs:

(try 
    (throw 
    (ex-info "The ice cream has melted!" 
     {:causes    #{:fridge-door-open :dangerously-high-temperature} 
     :current-temperature {:value 25 :unit :celcius}})) 
    (catch Exception e (ex-data e)) 

En un comentario Kolen mencionó slingshot, que proporciona una funcionalidad avanzada que le permite no sólo para arrojar los objetos de tipo arbitrario (con lanzamiento +), sino también utilizar una sintaxis de captura más flexible para inspeccionar datos dentro de objetos lanzados (con try +). Ejemplos de the project repo:

tensor/parse.clj

(ns tensor.parse 
    (:use [slingshot.slingshot :only [throw+]])) 

(defn parse-tree [tree hint] 
    (if (bad-tree? tree) 
    (throw+ {:type ::bad-tree :tree tree :hint hint}) 
    (parse-good-tree tree hint))) 

matemáticas/expression.clj

(ns math.expression 
    (:require [tensor.parse] 
      [clojure.tools.logging :as log]) 
    (:use [slingshot.slingshot :only [throw+ try+]])) 

(defn read-file [file] 
    (try+ 
    [...] 
    (tensor.parse/parse-tree tree) 
    [...] 
    (catch [:type :tensor.parse/bad-tree] {:keys [tree hint]} 
     (log/error "failed to parse tensor" tree "with hint" hint) 
     (throw+)) 
    (catch Object _ 
     (log/error (:throwable &throw-context) "unexpected error") 
     (throw+)))) 
Cuestiones relacionadas