Clojure 程序流-一次计算失败时退出操作

Clojure 程序流-一次计算失败时退出操作,clojure,Clojure,对不起,如果这个问题没有任何意义 我目前正在编写一个小应用程序,我想将一些函数“链接”在一起,形成一个更广泛的计算 例如,我有一个函数,它调用一个Web服务并返回一个散列映射,或者nil,如果是一个错误或出现了问题。链中的下一个函数获取映射并进行进一步处理,然后将其传递给下一个函数…依此类推 问题是,如果第一个函数失败,它将把nil传递给下一个函数,这将抛出一个空指针(或其他什么),我甚至不希望它达到这个阶段。 换句话说,如果链中的一项失败,我希望整个计算失败 e、 g 问题是我不想一开始就用i

对不起,如果这个问题没有任何意义

我目前正在编写一个小应用程序,我想将一些函数“链接”在一起,形成一个更广泛的计算

例如,我有一个函数,它调用一个Web服务并返回一个
散列映射
,或者
nil
,如果是一个错误或出现了问题。链中的下一个函数获取映射并进行进一步处理,然后将其传递给下一个函数…依此类推

问题是,如果第一个函数失败,它将把
nil
传递给下一个函数,这将抛出一个空指针(或其他什么),我甚至不希望它达到这个阶段。 换句话说,如果链中的一项失败,我希望整个计算失败

e、 g

问题是我不想一开始就用
if(nil?arg)
乱丢每个函数,理想情况下,我希望有一个抽象可以为我解决这个问题,但我并不真正了解Clojure中提供的功能

我正在考虑采用Scala风格的
选项
类型,它可以是
Some(value)
None
,但我仍然需要在开始时对代码进行检查

任何想法或回复都将非常感谢

,其中包括Scala调用的
选项
的monad实现。它被称为
maybe-m
,其工作原理是将
nil
视为
None
。您可以这样使用它:

(ns mulk.monads-test
  (:refer-clojure)
  (:use clojure.repl
        clojure.algo.monads))

(defn function1 [x]
  x)

(defn function2 [x]
  (+ x 10))

(defn function3 [x]
  (* x 2))

(defn calc-stuff [thing]
  (domonad maybe-m
    [x1 (function1 thing)
     x2 (function2 x1)
     x3 (function3 (+ x2 10))]
    x3))

 (calc-stuff 10)   ;=> 60
 (calc-stuff nil)  ;=> nil
(chain "http://webservice.com" function1 function2 function3 function4)

clojure.contrib.core有一个
-?>
宏,它可以完全满足您的需要


请参见

您可以定义一个助手函数,用于链接函数调用并检查其间的nil值:

(defn chain [v & functions]
  (cond (nil? v) nil
        (empty? functions) v
        :else (recur ((first functions) v) (rest functions))))
那么就这样称呼它:

(ns mulk.monads-test
  (:refer-clojure)
  (:use clojure.repl
        clojure.algo.monads))

(defn function1 [x]
  x)

(defn function2 [x]
  (+ x 10))

(defn function3 [x]
  (* x 2))

(defn calc-stuff [thing]
  (domonad maybe-m
    [x1 (function1 thing)
     x2 (function2 x1)
     x3 (function3 (+ x2 10))]
    x3))

 (calc-stuff 10)   ;=> 60
 (calc-stuff nil)  ;=> nil
(chain "http://webservice.com" function1 function2 function3 function4)

太棒了,这就是我一直在寻找的,看起来这个库中还有一些对我非常有用的抽象!啊哈!好东西。我想知道
-?>
宏是否实际上只是Matthias回答中描述的
maybe-m
单子的包装器?不,实现是自包含的: