首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >Clojure中的自动TCO

Clojure中的自动TCO
EN

Stack Overflow用户
提问于 2012-04-18 23:38:17
回答 2查看 1.4K关注 0票数 1

有没有办法在Clojure中定义一个自动尾部调用优化的函数?

例如:

代码语言:javascript
复制
(defrecur fact [x]
    (if (= x 1)
        1
        (* x (fact (dec x)))))

会在内部翻译成类似这样的内容:

代码语言:javascript
复制
(defn fact [x]
    (loop [n x f 1]
        (if (= n 1)
            f
            (recur (dec n) (* f n)))))

你能告诉我这样的东西是不是已经存在了?

EN

回答 2

Stack Overflow用户

发布于 2012-04-18 23:43:26

简短的回答是“不”。

稍微长一点的答案是,Clojure被故意设计成需要明确指示需要尾部调用优化的地方,因为JVM本身并不支持它。

顺便说一句,您可以在不使用loop的情况下使用recur,因此不需要更多的输入,例如:

代码语言:javascript
复制
(defn func [x]
  (if (= x 1000000)
    x
    (recur (inc x))))

更新,4月29日:

Chris Frisz一直在与Dan Friedman合作一个研究项目,虽然目前还没有人声称它是“答案”,但这个项目既有趣又有前途。克里斯最近做了一个关于这个项目和he's posted it on his blog的非正式演讲。

票数 2
EN

Stack Overflow用户

发布于 2012-04-18 23:45:19

据我所知,在Clojure中没有自动生成尾递归的方法。

有一些使用递归而不使用循环的函数示例。在不溢出堆栈的情况下重复该工作。这是因为这些函数都是精心编写的,以便使用惰性序列。

下面是一个用手写函数替换flatten的示例。这个例子来自于http://yyhh.org/blog/2011/05/my-solutions-first-50-problems-4clojure-com

代码语言:javascript
复制
(fn flt [coll]
  (let [l (first coll) r (next coll)]
    (concat 
      (if (sequential? l)
        (flt l)
        [l])
      (when (sequential? r)
        (flt r)))))
票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/10212928

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档