Hmmm...  if we take a look at the first arglist...

[name doc-string? attr-map? [params*] body]

Each of this expects a different type of object right?

name - clojure.lang.Symbol
doc-string? - java.lang.String
attr-map? clojure.lang.IPeristentMap
params* - IPeristentVector
body - IPerisistentSeq

What if we used c.c.seq-utils/group-by with class?  This would create
hash map with the appropriate values options in it.  From there it's a
simple matter of processing a map.  I think that the aritiy overloaded
version of defn is easy enough to detect to.  Would that do the trick?

Sean

On Dec 29, 1:15 pm, Rich Hickey <richhic...@gmail.com> wrote:
> On Sat, Dec 19, 2009 at 3:58 PM, Stuart Halloway
>
>
>
>
>
> <stuart.hallo...@gmail.com> wrote:
> > In Clojure it is idiomatic to have optional args at the front of the
> > signature. This makes it easy to define convenient caller APIs, but it
> > leads to bulky let forms like this one (from clojure.core/defmulti)
>
> >   (let [docstring   (if (string? (first options))
> >                       (first options)
> >                       nil)
> >         options     (if (string? (first options))
> >                       (next options)
> >                       options)
> >         m           (if (map? (first options))
> >                       (first options)
> >                       {})
> >         options     (if (map? (first options))
> >                       (next options)
> >                       options)
> >         dispatch-fn (first options)
> >         options     (next options)
> >         m           (assoc m :tag 'clojure.lang.MultiFn)
> >         m           (if docstring
> >                       (assoc m :doc docstring)
> >                       m)
> >         m           (if (meta mm-name)
> >                       (conj (meta mm-name) m)
> >                       m)]
>
> > Is it worth capturing this common idiom in a helper function, e.g. pop-
> > optional-args:
>
> > (defn pop-optional-args
> >   [preds args]
> >   (if (seq preds)
> >     (if ((first preds) (first args))
> >       (cons (first args) (pop-optional-args (rest preds) (rest args)))
> >       (cons nil (pop-optional-args (rest preds) args)))
> >     (list args)))
>
> > The above let form would then be:
>
> >   (let [[docstring m dispatch-fn options] (pop-optional-args [string?
> > map? identity] options)
> >         m           (assoc m :tag 'clojure.lang.MultiFn)
> >         m           (if docstring
> >                       (assoc m :doc docstring)
> >                       m)
> >         m           (if (meta mm-name)
> >                       (conj (meta mm-name) m)
> >                       m)]
>
> > Worth doing? If so, how could it be better?
>
> It's tough to guess as to the general applicability of this. One thing
> for sure, it's not really about args, more like a 'take-' or 'split-'
> variant. Finding a good name might point the way towards a general
> utility.
>
> Rich

-- 
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

Reply via email to