尽管我已经在 Linux 上使用 Common Lisp 一段时间了,但我在 Mac 上使用 SBCL 的经验仍然几乎为零。
我刚刚使用自制程序在 Mac (Sonoma 14.2.1) 上安装了 SBCL。
我现在有:SBCL 2.4.1
我在以下测试中遇到了一个问题。
这是测试程序:
me % cat test.lisp
#!/opt/homebrew/bin/sbcl --script
(with-input-from-string (strm (car *args*)) (setf ArgOne (read strm)))
(with-input-from-string (strm (cadr *args*)) (setf ArgTwo (read strm)))
(format "Argument One = ~a~%" ArgOne)
(format "Argument Two = ~a~%" ArgTwo)
me %
当这个相同的程序(除了第一行)在 debian 上的 clisp 下运行时,如下所示:
me % ./test.lisp 11 23
它会产生:
Argument One = 11
Argument Two = 23
正如我所料。
但是当在 mac 上的 sbcl 下运行时,如下所示:
me % ./test.lisp 11 23
它产生了这个意想不到的输出:
; file: /...././test.lisp
; in: WITH-INPUT-FROM-STRING (STRM (CAR *ARGS*))
; (CAR *ARGS*)
;
; caught WARNING:
; undefined variable: COMMON-LISP-USER::*ARGS*
; (SETF ARGONE (READ STRM))
;
; caught WARNING:
; undefined variable: COMMON-LISP-USER::ARGONE
;
; compilation unit finished
; Undefined variables:
; *ARGS* ARGONE
; caught 2 WARNING conditions
Unhandled UNBOUND-VARIABLE in thread #<SB-THREAD:THREAD "main thread" RUNNING
{7005550003}>:
The variable *ARGS* is unbound.
Backtrace for: #<SB-THREAD:THREAD "main thread" RUNNING {7005550003}>
0: ((LAMBDA NIL :IN "/..../test.lisp"))
1: (SB-INT:SIMPLE-EVAL-IN-LEXENV (WITH-INPUT-FROM-STRING (STRM (CAR *ARGS*)) (SETF ARGONE (READ STRM))) #<NULL-LEXENV>)
2: (EVAL-TLF (WITH-INPUT-FROM-STRING (STRM (CAR *ARGS*)) (SETF ARGONE (READ STRM))) 0 NIL)
3: ((LABELS SB-FASL::EVAL-FORM :IN SB-INT:LOAD-AS-SOURCE) (WITH-INPUT-FROM-STRING (STRM (CAR *ARGS*)) (SETF ARGONE (READ STRM))) 0)
4: ((LAMBDA (SB-KERNEL:FORM &KEY :CURRENT-INDEX &ALLOW-OTHER-KEYS) :IN SB-INT:LOAD-AS-SOURCE) (WITH-INPUT-FROM-STRING (STRM (CAR *ARGS*)) (SETF ARGONE (READ STRM))) :CURRENT-INDEX 0)
5: (SB-C::%DO-FORMS-FROM-INFO #<FUNCTION (LAMBDA (SB-KERNEL:FORM &KEY :CURRENT-INDEX &ALLOW-OTHER-KEYS) :IN SB-INT:LOAD-AS-SOURCE) {1005F0E1B}> #<SB-C::SOURCE-INFO {70055166F3}> SB-C::INPUT-ERROR-IN-LOAD)
6: (SB-INT:LOAD-AS-SOURCE #<SB-SYS:FD-STREAM for "file /...././test.lisp" {7005510D73}> :VERBOSE NIL :PRINT NIL :CONTEXT "loading")
7: ((LABELS SB-FASL::LOAD-STREAM-1 :IN LOAD) #<SB-SYS:FD-STREAM for "file /...././test.lisp" {7005510D73} > NIL)
8: (SB-FASL::CALL-WITH-LOAD-BINDINGS #<FUNCTION (LABELS SB-FASL::LOAD-STREAM-1 :IN LOAD) {1005F09EB}> #<SB-SYS:FD-STREAM for "file /...././test.lisp" {7005510D73}> NIL #<SB-SYS:FD-STREAM for "file /...././ test.lisp" {7005510D73}>)
9: (LOAD #<SB-SYS:FD-STREAM for "file /...././test.lisp" {7005510D73}> :VERBOSE NIL :PRINT NIL :IF-DOES-NOT-EXIST :ERROR :EXTERNAL-FORMAT :DEFAULT)
10: ((FLET SB-IMPL::LOAD-SCRIPT :IN SB-IMPL::PROCESS-SCRIPT) #<SB-SYS:FD-STREAM for "file /...././test. lisp" {7005510D73}>)
11: ((FLET SB-UNIX::BODY :IN SB-IMPL::PROCESS-SCRIPT))
12: ((FLET "WITHOUT-INTERRUPTS-BODY-11" :IN SB-IMPL::PROCESS-SCRIPT))
13: (SB-IMPL::PROCESS-SCRIPT "./test.lisp")
14: (SB-IMPL::TOPLEVEL-INIT)
15: ((FLET SB-UNIX::BODY :IN SB-IMPL::START-LISP))
16: ((FLET "WITHOUT-INTERRUPTS-BODY-3" :IN SB-IMPL::START-LISP))
17: (SB-IMPL::%START-LISP)
unhandled condition in --disable-debugger mode, quitting
me %
显然存在一些我不知道的与我应该如何使用 SBCL 相关的问题。
任何 lisp 专家或具有 SBCL 知识的更好的人都将非常感激告诉我应该如何做事情。
sbcl
的 argv 位于其中*posix-argv*
,第一个参数是 sbcl。将您的 clisp 程序修改为 sbcl 可运行程序是
为了让它们可移植,在不同的实现上以相同的方式,使用
(uiop:command-line-arguments)
.您可能需要
(require :uiop)
,但 ASDF(以及 UIOP)在大多数(不是说全部)实现中都已提供。要正确解析CLI 参数,请使用 Clingon 等库。
请参阅: https: //lispcookbook.github.io/cl-cookbook/scripting.html