我真正想要的是源内测试定义:
假设我有一个asdf系统:
(defsystem simple-system
:serial t
:components ((:module "src"
:components
((:file "0-package")
(:file "1-tests-stubs")
(:file "2-code") ...))))
另一个测试第一个的系统:
(defsystem simple-system-tests
:serial t
:components ((:module "src"
:components
((:file "0-package")
(:file "1-tests-real")
(:file "2-code") ...))))
它们之间的唯一区别在于simple-system
我1-tests-stubs
simple-system-tests
1-tests-real
1-tests-stubs
(defmacro def-test (&rest _args) nil)
。
在1-tests-real
中,我定义了一个宏simple-system
,它可以获得真实的'在(declare (optimize (safety 0) (debug 0) (speed 3)))
。
现在我想用simple-system-tests
编译(declare (optimize (safety 3) (debug 3) (speed 0)))
,用simple-system
编译simple-system-tests
。
我该怎么做(在这里放置以及如何以通用的方式为这两个系统设置这些声明)?
如何在{{1}}中重用{{1}}的定义(不重复自己重新输入所有模块/组件)?
我必须确保所有文件都针对每个系统重新编译,具有不同的优化级别。
此外,如果每个系统文件只有在更改后才会重新编译(每个系统的编译文件的自己副本?),那将会很棒。
答案 0 :(得分:3)
目前这是部分答案。
您可以尝试使用:around-compile
:
(defsystem simple-system
:serial t
:around-compile (lambda (next)
(proclaim '(optimize (debug 3)
(safety 3)
(debug 3)
(speed 0)))
(funcall next))
:components ((:module "src"
:components
(...))))
文件说(强调我的):
使用此钩子,您可以实现以下效果:本地重命名包,绑定* readtables *和其他语法控制变量,处理警告和其他条件,宣布一致的优化设置,从而节省代码覆盖率信息,维护有关编译时序的元数据,设置gensym计数器和PRNG种子以及其他非确定性来源,覆盖源位置和/或时间戳系统,检查一些编译时副作用是否得到适当平衡等。
围绕系统中正在编译的每个文件执行操作;您可以为模块中的所有文件或特定文件隐藏:around-compile
的值。
答案 1 :(得分:2)
安全性低的优化。
通常我会不建议编译整个系统(库或应用程序),安全性为零,如下所示:
(declare (optimize (safety 0) (debug 0) (speed 3)))
将零安全性与组合声明结合使用可能会改变程序的语义,错误可能会导致程序崩溃。它甚至可能会打开安全漏洞。
我对生产代码的建议如下:
使用speed
= 3优化速度关键部件并保留通常的安全设置(2或3)。
如果需要低安全设置以进一步提高速度,请仅在需要时进行声明。 Common Lisp提供了函数局部声明,还提供了一个特殊的运算符locally,其中还可以限制声明适用的代码区域。
优化设置可更改
* (defparameter *safety* 0)
这不起作用,因为安全值必须是数字:
*SAFETY*
* (defun foo (a) (declare (optimize (safety *safety*))) (1+ a))
; in: DEFUN FOO
; (OPTIMIZE (SAFETY *SAFETY*))
;
; caught WARNING:
; Ignoring bad optimization value *SAFETY* in: (OPTIMIZE (SAFETY *SAFETY*))
;
; compilation unit finished
; caught 1 WARNING condition
FOO
但这可行,使用阅读时评估:
* (defun foo (a) (declare (optimize (safety #.*safety*))) (1+ a))
WARNING: redefining COMMON-LISP-USER::FOO in DEFUN
FOO
还可以插入整个声明:
* (defparameter *optimization-declaration* '(declare (optimize (safety 0))))
*OPTIMIZATION-DECLARATION*
* (defun foo (a) #.*optimization-declaration* (1+ a))
WARNING: redefining COMMON-LISP-USER::FOO in DEFUN
FOO
*
答案 2 :(得分:0)
我希望这只是一个错字,在这些示例中,两个系统共享相同的文件0包。如果不是,你将会失败,这将是你的全部错误。