如果我在 emacs-lisp 中编写这个函数:
(defun factorial (n)
(if (<= n 1)
1
(* n (factorial (- n 1)))))
=> factorial
它适用于像 5 或 10 这样的小数,但如果我尝试计算(阶乘 33)答案是 -1211487723752259584,这显然是错误的,所有大数都会破坏函数。在 python 中,这不会发生。是什么导致了这个问题?
calc
在处理大量数字时,您总是可以调用 Emacs 的库。
(defun factorial (n)
(string-to-number (factorial--1 n)))
(defun factorial--1 (n)
(if (<= n 1)
"1"
(calc-eval (format "%s * %s"
(number-to-string n)
(factorial--1 (- n 1))))))
ELISP> (factorial 33)
8.683317618811886e+036
进一步阅读:
(calc)
RET(calc) Calling Calc from Your Programs
RET整数有一个特定的范围。超出此范围的值无法表示。这是大多数(但不是全部)编程语言的标准。您可以通过检查most-positive-fixnum
.
转到您的*scratch*
缓冲区(或任何 Lisp 缓冲区)并输入most-positive-fixnum
. 将光标放在末尾,然后按C-x C-e
。在我的电脑上,我得到 2305843009213693951 作为值。你的可能会有所不同:我在 64 位机器上,这个数字大约是2^61
. 33 的阶乘的解是 8683317618811886495518194401280000000。大约是 2^86,这也超出了我的 Emacs 可以处理的范围。(我使用Arc来精确计算它,因为 Arc 可以表示任何大小的整数,受制于您安装的内存量等无聊的东西)。
最简单的解决方案似乎是保罗的解决方案:
(defun factorial (n) (calc-eval (format "%s!" n)))
ELISP> (factorial 33)
8683317618811886495518194401280000000
但是,我尝试通过另一种 Calc 方式来取乐,而不使用calc-eval
and string
。因为使用 Calc 的更复杂的 Emacs Lisp 程序可以通过这种方式完成。
Calcdefmath
和calcFunc-
函数在 Emacs Lisp 中非常强大。
(defmath myFact (n) (string-to-number (format-number (calcFunc-fact n))))
ELISP> (calcFunc-myFact 33)
8.683317618811886e+36
我找到了这个问题,寻找一种在 Elisp 中计算阶乘的快速简便的方法,最好不实现它。
从其他答案中,我推测它是:
(calc-eval "10!")
这相当于
(calc-eval "fact(10)")
它与重新定义阶乘函数一样简洁且功能更强大。例如,您可以通过这种方式获得二项式系数:
(calc-eval "7!/3!(7-3)!")
甚至这样:
(calc-eval "choose(7,3)")
Calc真的很值得探索。我建议在 Emacs 中做交互式教程。您可以使用C-x
*
t
. 至于 calc,您可以将其与C-x
*
c
、 或 一起使用M-x
calc
。