<?xml version="1.0" encoding="utf-8"?>
<rss version="2.0">
<channel>
<title>Clojure Q&amp;A - Recent questions tagged fn</title>
<link>https://ask.clojure.org/index.php/tag/fn</link>
<description></description>
<item>
<title>Destructuring {:as opts} unexpected behaviour with seq</title>
<link>https://ask.clojure.org/index.php/15028/destructuring-as-opts-unexpected-behaviour-with-seq</link>
<description>&lt;p&gt;Hi,&lt;/p&gt;
&lt;p&gt;I found out something weird in some old code, where I wanted to pass the first map in a sequence and by mistake the code was working while actually passing the sequence itself!&lt;/p&gt;
&lt;p&gt;After digging to make sense of this, I found out it has to do with the &lt;code&gt;{:as opts}&lt;/code&gt; destructuring.&lt;/p&gt;
&lt;p&gt;Here's some code:&lt;/p&gt;
&lt;pre&gt;&lt;code&gt;;; even if something is assigned sequential vs associative
;; the `:as` is transparent
(let [[:as opts] {1 2 3 4}]
  opts)
#_=&amp;gt; {1 2, 3 4}
(let [{:as opts} [1 2 3 4]]
  opts)
#_=&amp;gt; [1 2 3 4]
;; however with a seq it's returned as a map
(let [{:as opts} (seq [1 2 3 4])]
  opts)
#_=&amp;gt; {1 2, 3 4}

;; and it only gets weirder!
(let [{:as opts} (seq [{:k :v}])]
  opts)
#_=&amp;gt; {:k :v}
(let [{:as opts} (seq [{:k1 :v1} {:k2 :v2}])]
  opts)
#_=&amp;gt; {{:k1 :v1} {:k2 :v2}}
(let [{:as opts} (seq [{:k1 :v1} {:k2 :v2} {:k3 :v3}])]
  opts)
#_=&amp;gt; {{:k1 :v1} {:k2 :v2}, :k3 :v3}
(let [{:as opts} (seq [{:k1 :v1} {:k2 :v2} :not-a-map])]
  opts)
;; java.lang.IllegalArgumentException: Don't know how to create ISeq from: clojure.lang.Keyword
(let [{:as opts} (seq [1 2 3])]
  opts)
;; java.lang.IllegalArgumentException: Don't know how to create ISeq from: java.lang.Long
&lt;/code&gt;&lt;/pre&gt;
&lt;p&gt;In my case I didn't realize my code was wrong because &lt;code&gt;{:as opts} {:k :v}&lt;/code&gt; is the same as &lt;code&gt;{:as opts} (seq [{:k :v}])&lt;/code&gt;.&lt;/p&gt;
&lt;p&gt;To me this is behaviour I would expect closer to &lt;code&gt;&amp;amp; {:as opts}&lt;/code&gt; rather than just plain map destructuring &lt;code&gt;{:as opts}&lt;/code&gt;. Maybe both behaviours should be separated?&lt;/p&gt;
&lt;p&gt;I think this should be tackled either by&lt;br&gt;
1. make &lt;code&gt;:as&lt;/code&gt; transparent regardless of what comes in to always bind&lt;br&gt;
2. throw an error earlier when it's not of the expected destructuring&lt;br&gt;
3. Document this very unexpected edge case in &lt;a rel=&quot;nofollow&quot; href=&quot;https://clojure.org/reference/special_forms#associative-destructuring&quot;&gt;https://clojure.org/reference/special_forms#associative-destructuring&lt;/a&gt;&lt;br&gt;
4. Separate the keyword arguments use case from plain map destructuring? (Assuming both are now mixed together)&lt;/p&gt;
</description>
<category>Sequences</category>
<guid isPermaLink="true">https://ask.clojure.org/index.php/15028/destructuring-as-opts-unexpected-behaviour-with-seq</guid>
<pubDate>Sat, 04 Apr 2026 23:50:39 +0000</pubDate>
</item>
<item>
<title>A function with metadata is slower than it could be</title>
<link>https://ask.clojure.org/index.php/14438/a-function-with-metadata-is-slower-than-it-could-be</link>
<description>&lt;p&gt;I found that &lt;code&gt;with-meta&lt;/code&gt; applied to a function returns an instance of &lt;code&gt;RestFn&lt;/code&gt;.&lt;br&gt;
However, I know that invoking a function through &lt;code&gt;applyTo&lt;/code&gt; is much slower than through &lt;code&gt;invoke&lt;/code&gt;.&lt;br&gt;
The benchmarks in :thread: confirm this.&lt;/p&gt;
&lt;p&gt;Is it a problem that a function with metadata is slower than it could be?&lt;/p&gt;
&lt;p&gt;If so, I could propose a solution - to proxy all methods like &lt;code&gt;invoke&lt;/code&gt; to the original function, not just &lt;code&gt;applyTo&lt;/code&gt;.&lt;/p&gt;
&lt;p&gt;&lt;a rel=&quot;nofollow&quot; href=&quot;https://github.com/clojure/clojure/blob/master/src/jvm/clojure/lang/AFunction.java#L31-L33&quot;&gt;https://github.com/clojure/clojure/blob/master/src/jvm/clojure/lang/AFunction.java#L31-L33&lt;/a&gt;&lt;/p&gt;
&lt;pre&gt;&lt;code&gt;(require '[criterium.core :as c])

(defn f [x]
  x)

(c/quick-bench
    (f 1))
;; Execution time mean : 1,642094 ns

(defn wrapper [f]
  (fn [y]
    (f y)))

(let [f' (wrapper f)]
  (c/quick-bench (f' 1)))
;; Execution time mean : 5,016630 ns

(let [f'' (with-meta f {:foo :bar})]
  (c/quick-bench (f'' 1)))
;; Execution time mean : 31,332965 ns

(defn wrapper' [f]
  (fn [&amp;amp; args]
    (apply f args)))

(let [f''' (wrapper' f)]
  (c/quick-bench (f''' 1)))
;; Execution time mean : 41,983970 ns
&lt;/code&gt;&lt;/pre&gt;
&lt;p&gt;Additional links:&lt;br&gt;
 - &lt;a rel=&quot;nofollow&quot; href=&quot;https://clojurians.slack.com/archives/C03S1KBA2/p1740750168290999&quot;&gt;https://clojurians.slack.com/archives/C03S1KBA2/p1740750168290999&lt;/a&gt;&lt;br&gt;
 - &lt;a rel=&quot;nofollow&quot; href=&quot;https://github.com/camsaul/methodical/pull/150&quot;&gt;https://github.com/camsaul/methodical/pull/150&lt;/a&gt;&lt;/p&gt;
</description>
<category>Metadata</category>
<guid isPermaLink="true">https://ask.clojure.org/index.php/14438/a-function-with-metadata-is-slower-than-it-could-be</guid>
<pubDate>Mon, 03 Mar 2025 07:20:38 +0000</pubDate>
</item>
<item>
<title>Macroexpanding a macro with `fn` crashes with &quot;fn did not conform to spec&quot;</title>
<link>https://ask.clojure.org/index.php/11449/macroexpanding-macro-with-crashes-with-did-not-conform-spec</link>
<description>&lt;p&gt;The following code crashes:&lt;/p&gt;
&lt;pre&gt;&lt;code&gt;(defmacro m []
  `(fn [x]))

(macroexpand '(m))
&lt;/code&gt;&lt;/pre&gt;
&lt;p&gt;The error is:&lt;/p&gt;
&lt;blockquote&gt;&lt;p&gt;Call to clojure.core/fn did not conform to spec&lt;br&gt;
[...]&lt;br&gt;
:reason &quot;Extra input&quot;&lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;The following code does not crash and works as expected:&lt;/p&gt;
&lt;pre&gt;&lt;code&gt;(defmacro m []
  `(asdfasdf [x]))

(macroexpand '(m))
&lt;/code&gt;&lt;/pre&gt;
&lt;p&gt;How does the first snippet crash when the macro should just be returning a quoted piece of code? Why does it run &lt;code&gt;fn&lt;/code&gt; at all?&lt;/p&gt;
</description>
<category>Macros</category>
<guid isPermaLink="true">https://ask.clojure.org/index.php/11449/macroexpanding-macro-with-crashes-with-did-not-conform-spec</guid>
<pubDate>Tue, 11 Jan 2022 08:29:50 +0000</pubDate>
</item>
<item>
<title>Macro for threading lambda expression</title>
<link>https://ask.clojure.org/index.php/10749/macro-for-threading-lambda-expression</link>
<description>&lt;p&gt;It is common to have lambda functions with one argument for things like map, filter, find, etc.  &lt;/p&gt;
&lt;p&gt;I think could be usefull a macro that do something like &lt;code&gt;(fn-&amp;gt;  :value inc  (&amp;gt; 1))&lt;/code&gt; which would be equivalent of   &lt;code&gt;#(-&amp;gt; % :value inc  (&amp;gt; 1))&lt;/code&gt;&lt;/p&gt;
&lt;p&gt;Something like  &lt;/p&gt;
&lt;pre&gt;&lt;code&gt;(defmacro fn-&amp;gt;
  [&amp;amp; forms]
  `(fn [x#] (-&amp;gt; x# ~@forms)))
(defmacro fn-&amp;gt;&amp;gt;
  [&amp;amp; forms]
  `(fn [x#] (-&amp;gt;&amp;gt; x# ~@forms)))
&lt;/code&gt;&lt;/pre&gt;
&lt;p&gt;I see this a very useful for readability if in the core library. wdyt?&lt;/p&gt;
</description>
<category>Macros</category>
<guid isPermaLink="true">https://ask.clojure.org/index.php/10749/macro-for-threading-lambda-expression</guid>
<pubDate>Fri, 02 Jul 2021 16:53:46 +0000</pubDate>
</item>
</channel>
</rss>