lisp - 如何在 Lisp 中格式化我的 REPL 输出的数字精度?

标签 lisp common-lisp number-formatting

我的问题是:
如何设置 REPL 打印输出的精度?

例如,这里的这个简单函数:

(defun gaussian (rows cols sigma)
  (let ((filter (make-array `(,rows ,cols)))
    (rowOffset (/ (- rows 1) 2.0))
    (colOffset (/ (- cols 1) 2.0)))
    (loop for i from 0 to (- rows 1)
       do (loop for j from 0 to (- cols 1)
           do (setf (aref filter i j)
            (gaussDistVal i j rowOffset ColOffset sigma))))
    filter))

如果我调用 (gaussian 5 5 1),我的输出如下:

#2A((0.01831564 0.082085 0.13533528 0.082085 0.01831564)
    (0.082085 0.36787945 0.60653067 0.36787945 0.082085)
    (0.13533528 0.60653067 1.0 0.60653067 0.13533528)
    (0.082085 0.36787945 0.60653067 0.36787945 0.082085)
    (0.01831564 0.082085 0.13533528 0.082085 0.01831564))

而我想得到:

#2A((0.0 0.1 0.1 0.1 0.0)
    (0.0 0.4 0.6 0.4 0.1)
    (0.1 0.6 1.0 0.6 0.1)
    (0.0 0.4 0.6 0.4 0.1)
    (0.0 0.1 0.1 0.1 0.0))

如果您有答案,能否也请告诉我这些“REPL 自定义”记录在何处?

(SBCL 1.2.11;Emacs 25 上的史莱姆)

最佳答案

使用 Common Lisp pretty-print

Common Lisp 具有广泛的 pretty printer .一个很少使用的功能是用于控制某种类型对象打印的调度表。参见 set-pprint-dispatch如何配置此功能。

format 函数具有输出各种形式的 float 的功能。

这个例子结合了两者:

CL-USER 32 > (set-pprint-dispatch 'float
                                  #'(lambda (s obj)
                                      (format s "~,1F" obj)))
NIL

CL-USER 33 > (setf *print-pretty* t)
T

CL-USER 34 > #2A((0.01831564 0.082085 0.13533528 0.082085 0.01831564)
                 (0.082085 0.36787945 0.60653067 0.36787945 0.082085)
                 (0.13533528 0.60653067 1.0 0.60653067 0.13533528)
                 (0.082085 0.36787945 0.60653067 0.36787945 0.082085)
                 (0.01831564 0.082085 0.13533528 0.082085 0.01831564))

#2A((0.0 0.1 0.1 0.1 0.0)
    (0.1 0.4 0.6 0.4 0.1)
    (0.1 0.6 1.0 0.6 0.1)
    (0.1 0.4 0.6 0.4 0.1)
    (0.0 0.1 0.1 0.1 0.0))

人们可能还想临时使用它:

CL-USER 37 > (let ((*print-pprint-dispatch* (copy-pprint-dispatch)))
               (set-pprint-dispatch 'float
                                    #'(lambda (s obj)
                                        (format s "~,1F" obj)))
               (pprint #2A((0.01831564 0.082085 0.13533528 0.082085 0.01831564)
                           (0.082085 0.36787945 0.60653067 0.36787945 0.082085)
                           (0.13533528 0.60653067 1.0 0.60653067 0.13533528)
                           (0.082085 0.36787945 0.60653067 0.36787945 0.082085)
                           (0.01831564 0.082085 0.13533528 0.082085 0.01831564))))

#2A((0.0 0.1 0.1 0.1 0.0)
    (0.1 0.4 0.6 0.4 0.1)
    (0.1 0.6 1.0 0.6 0.1)
    (0.1 0.4 0.6 0.4 0.1)
    (0.0 0.1 0.1 0.1 0.0))

关于lisp - 如何在 Lisp 中格式化我的 REPL 输出的数字精度?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/34301050/

相关文章:

lisp - Lisp 中的变量和符号是否不同?

clojure - 如何提高我的 clojure eratosthenes 算法的性能?

lisp - 在 Linux 中安装 SBCL

syntax-error - Lisp,指令在 defun 中不起作用

LISP MAKE-PATHNAME : Illegal :DIRECTORY argument

java - 将逗号插入大数字的方法

clojure - 什么时候在 Clojure 宏中使用 ~'some-symbol?

lisp - 闭包和动态作用域?

java - 使用随机逗号或点分隔符从文件中解析 double

ms-access - Val() 函数无法识别系统范围内的小数点