有没有类似Python的`if __name__ ==“__ main __”:`Common Lisp中的东西

时间:2012-01-03 14:16:31

标签: lisp common-lisp

我在两个独立的文件中写了两个函数,假设是文件A.lisp和B.lisp,其中两个文件都有一些用于测试的主程序代码,而A.lisp会调用B.lisp中的函数。这意味着直接在A.lisp中使用load方法将执行B.lisp中的主代码,这不应该发生。在我看来,这些文件太小了,不能用像包这样的东西。

在Common Lisp中有类似Python的if __name__ == "__main__":内容吗?只有当前文件是主模块(即正在运行的程序)时才会执行包含在此条件中的顶级代码,但如果它作为库导入则不会执行。

4 个答案:

答案 0 :(得分:6)

包只是符号的名称空间。他们没有说任何关于加载或编译代码的事情。

Common Lisp在ANSI Common Lisp标准中没有库,模块或类似“主”模块/例程的想法。该标准定义了两个例程PROVIDEREQUIRE。但那些指定并不是很明确。

大多数应用程序和库使用“系统”工具来构造,指定,编译和加载代码。

有一个名为ASDF的'免费'。 '另一个系统定义工具'。对于大多数类型的应用程序,像ASDF这样的工具很有用。对于原始应用程序,您可以使用COMPILE-FILELOAD等标准函数编写自己的工具。

Nick Levine为ASDF撰写了一个教程(他遗弃的Lisp书籍项目的一部分):Systems

有几个Lisp实现具有更广泛的工具来创建应用程序(例如使用Clozure Common Lisp编写的Mac OS X应用程序)。

答案 1 :(得分:4)

if __name__ == "__main__":成语非常特定于Python,甚至Python社区中的一些人也会考虑将它用于测试代码的错误样式。

Common Lisp高度重视REPL中的交互式开发,每次要运行测试时都必须重新加载整个文件。只需将测试放入函数定义而不是顶层,它就可以工作并且更方便。

答案 2 :(得分:2)

评估顶级表单。

您可以定义一个main函数,如下例所示,您可以随意调用该函数:

<强> a.lisp

(defun main ()
  ...)

<强> b.lisp

(load "a.lisp")
(main)

答案 3 :(得分:1)

我真的不知道它在Python中是如何工作的,但它看起来像一个文件 一个模块,两个文件是两个不同的模块。事实并非如此 Common Lisp。如果您没有定义任何包,那么当load文件时, 所有定义都将在当前包中提供(CL-USER是 默认)。这更像是将代码粘贴到REPL中。

但是包裹并不是很难使用。

在A.lisp:

(defpackage foo
  (:use #:cl)
  (:export main))

(in-package :foo)

(defun main ()
   (do-some-stuff)
   (baz:main some-args))
B.lisp中的

(defpackage baz
  (:use #:cl)
  (:export main))

(in-package :baz)

(defun main (some-args)
   (do-some-stuff))

你可以读 The Complete Idiot's Guide to Common Lisp PackagesPCL chapter on packages