为什么 sbcl common-lisp 中的集合差异似乎具有破坏性?
Why does set-difference in sbcl common-lisp appear to be destructive?
以下代码片段在 SBCL 2.2.3 下编译(使用 Emacs/SLIME,C-c C-k),并且 .fasl 加载没有错误。
在随后调用 REPL 中的测试集时,*evens* 的值设置为 *all*。阅读我能找到的文档,我无法弄清楚为什么会发生这种情况以及为什么调用测试集会导致 nil。预先感谢所有阅读 and/or 回复的人。
(defun get-n (n)
"Return a list of integers from 0 up to n-1"
(do ((i (1- n) (1- i))
(res nil (cons i res)))
((< i 0) res)))
(defun get-odd-n (n)
"Returns a list of odd integers from 1 up to n-1"
(do ((i (1- n) (1- i))
(res nil (if (oddp i)
(cons i res) res)))
((< i 0) res)))
(defun get-even-n (n)
"Returns a list of even integers from 0 up to n-1"
(do ((i (1- n) (1- i))
(res nil (if (evenp i)
(cons i res) res)))
((< i 0) res)))
(defconstant +n+ 10)
(defparameter *all* (get-n +n+))
(defparameter *odds* (get-odd-n +n+))
(defparameter *evens* (get-even-n +n+))
(defun test-sets ()
"After compiling and loading .fasl,
why is *evens* altered after calling test-sets?"
(and (equal (sort (intersection *evens* *all*) #'<) *evens*)
(equal (sort (intersection *odds* *all*) #'<) *odds*)
(equal (sort (union *odds* *evens*) #'<) *all*)
(equal (sort (set-difference *all* *odds* :test #'eql) #'<) *evens*)
(equal (sort (set-difference *all* *evens* :test #'eql) #'<) *odds*)))
UNION 结果与其输入共享列表结构。
SORT 具有破坏性。
->
SORT 更改列表结构,包括。列表结构 *evens*
指向。
解决方案:
或者:定义一个non-destructive SORT
或者:或者复制作为 SORT 参数的列表
(sort (copy-list ...) ...)
以下代码片段在 SBCL 2.2.3 下编译(使用 Emacs/SLIME,C-c C-k),并且 .fasl 加载没有错误。
在随后调用 REPL 中的测试集时,*evens* 的值设置为 *all*。阅读我能找到的文档,我无法弄清楚为什么会发生这种情况以及为什么调用测试集会导致 nil。预先感谢所有阅读 and/or 回复的人。
(defun get-n (n)
"Return a list of integers from 0 up to n-1"
(do ((i (1- n) (1- i))
(res nil (cons i res)))
((< i 0) res)))
(defun get-odd-n (n)
"Returns a list of odd integers from 1 up to n-1"
(do ((i (1- n) (1- i))
(res nil (if (oddp i)
(cons i res) res)))
((< i 0) res)))
(defun get-even-n (n)
"Returns a list of even integers from 0 up to n-1"
(do ((i (1- n) (1- i))
(res nil (if (evenp i)
(cons i res) res)))
((< i 0) res)))
(defconstant +n+ 10)
(defparameter *all* (get-n +n+))
(defparameter *odds* (get-odd-n +n+))
(defparameter *evens* (get-even-n +n+))
(defun test-sets ()
"After compiling and loading .fasl,
why is *evens* altered after calling test-sets?"
(and (equal (sort (intersection *evens* *all*) #'<) *evens*)
(equal (sort (intersection *odds* *all*) #'<) *odds*)
(equal (sort (union *odds* *evens*) #'<) *all*)
(equal (sort (set-difference *all* *odds* :test #'eql) #'<) *evens*)
(equal (sort (set-difference *all* *evens* :test #'eql) #'<) *odds*)))
UNION 结果与其输入共享列表结构。
SORT 具有破坏性。
->
SORT 更改列表结构,包括。列表结构 *evens*
指向。
解决方案:
或者:定义一个non-destructive SORT
或者:或者复制作为 SORT 参数的列表
(sort (copy-list ...) ...)