Che*_*tan 8 clojure integer-overflow lazy-evaluation
我只是学习在Clojure中使用延迟序列,我不确定我在下面的代码中做错了什么:
(defn sum [seqn]
(reduce + seqn))
(defn fib
([] (concat [0 1] (fib 0 1)))
([a b] (lazy-seq (cons (+ a b) (fib b (+ a b))))))
(defn up-to [n seqn]
(filter (fn [x] (< x n)) seqn))
(sum (up-to 100 (fib))) => ArithmeticException integer overflow clojure.lang.Numbers.throwIntOverflow (Numbers.java:1388)
Run Code Online (Sandbox Code Playgroud)
求和的数字不应大于100,那导致整数溢出的原因是什么?
从clojure 1.3.0开始,数字不会自动提升为bigInt/bigDecimal.
解决这个问题的使用+',而不是
你的第100个纤维蛋白数对于整数来说太大了
user> (nth (fib) 100)
354224848179261915075N
Run Code Online (Sandbox Code Playgroud)
过滤无限seq会产生无限seq,并且减少此值会导致过滤器继续查找另一个匹配项,即使谓词停止返回true也是如此.
替换filter为take-while.由此产生的无限序列(fib)将导致filter永远运行,但在此之前它将因ArithmeticException您正在经历而中断.take-while在(fn [x] (< x n))谓词评估为false 后,将停止对列表的进一步评估.
(defn up-to [n seqn]
(take-while (fn [x] (< x n)) seqn))
(sum (up-to 100 (fib))) ;; => 232
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
746 次 |
| 最近记录: |