I'm writing a maybe/state monad using clojure.contrib.monads. I've gotten by fine with using just (state-t maybe-m), but now I need different behavior: I need a monad that behaves precisely like (state-t maybe-m), except that when a monadic value mv is called on a state s and fails, (mv s) returns [::failure s] *instead of nil* (as maybe-m normally does). This is the difference.
Now I'm basically done, except I can't figure out a value of m-zero that fulfills the required axioms: - (m-bind m-zero f) produces m-zero - (m-bind mv (fn [x] m-zero)) produces m-zero This is what I have so far: (defmonad parser-m "The monad that FnParse uses." [m-zero (fn [state] [::failure state]) m-result (fn m-result-parser [product] (fn [state] [product state])) m-bind (fn m-bind-parser [rule product-fn] (fn [state] (let [result (rule state)] (if (failure? result) result (let [[product new-state] result] ((product-fn product) new-state)))))) m-plus (fn m-plus-parser [& rules] (fn [state] (or (first (drop-while failure? (map #(% state) rules))) (m-zero state))))]) The first axiom is fulfilled: user=> (def a (m-bind m-zero (constantly [5 [2 3]]))) #'user/a user=> (a [0 1]) [:user/failure [0 1]] user=> (m-zero [0 1]) [:user/failure [0 1]] But the second is not: user=> (def b (m-bind (constantly [:x [1 2]]) m-zero)) #'user/b user=> (b [0 1]) And no matter what I do, I can't fulfill that second axiom. Has anyone created this type of monad before? It seems like it should be a common pattern: exactly like (state-t maybe-m), only failures are vector pairs too. -- You received this message because you are subscribed to the Google Groups "Clojure" group. To post to this group, send email to clojure@googlegroups.com Note that posts from new members are moderated - please be patient with your first post. To unsubscribe from this group, send email to clojure+unsubscr...@googlegroups.com For more options, visit this group at http://groups.google.com/group/clojure?hl=en