Примечание: я написал этот ответ в ответ на мое первоначальное понимание проблемы, когда я подумал, что изображение все еще было «грязным» из-за какого-то предыдущего кода. Это частый случай подобных симптомов. Этот случай, однако, возникает из-за того, что эффекты use-package
проявляются не во время компиляции, а во время загрузки. Таким образом, когда я load
файл ниже, проблем нет, но при компиляции его как OP есть ссылка на cl-user::divisble-by
. Я оставляю этот ответ здесь, потому что люди с этой проблемой, скорее всего, ее найдут, но это не совсем та же проблема, что и у OP.
Ваш код:
Я сделал локальные копии вашего кода в util.lisp
и file2.lisp
:
$ cat util.lisp
(defpackage :euler-util
(:use :common-lisp)
(:export :divisible-by))
(in-package :euler-util)
(defun divisible-by (x y)
(equal 0 (mod x y)))
$ cat file2.lisp
(load "util.lisp")
(use-package :euler-util)
(defun euler-1 ()
(loop for i from 3 to 999 when (or (divisible-by i 3) (divisible-by i 5)) sum i))
Воспроизведение проблемы
Эту проблему легко воспроизвести: если вы каким-то образом внедрили символ a с именем "DIVISIBLE-BY"
в пакет CL-USER
, а затем попытаетесь использовать пакет, который экспортирует символ с тем же именем, у вас возникнут проблемы:
$ sbcl --noinform
* (defun divisible-by (&rest args) (declare (ignore args)))
DIVISIBLE-BY
* (load "file2")
debugger invoked on a NAME-CONFLICT in thread #<THREAD "initial thread" RUNNING
{1002979041}>:
USE-PACKAGE #<PACKAGE "EULER-UTIL"> causes name-conflicts in
#<PACKAGE "COMMON-LISP-USER"> between the following symbols:
EULER-UTIL:DIVISIBLE-BY, COMMON-LISP-USER::DIVISIBLE-BY
See also:
The ANSI Standard, Section 11.1.1.2.5
Type HELP for debugger help, or (SB-EXT:QUIT) to exit from SBCL.
restarts (invokable by number or by possibly-abbreviated name):
0: [RESOLVE-CONFLICT] Resolve conflict.
1: [RETRY ] Retry EVAL of current toplevel form.
2: [CONTINUE ] Ignore error and continue loading file "…/file2.lisp".
3: [ABORT ] Abort loading file "…/file2.lisp".
4: Exit debugger, returning to top level.
(NAME-CONFLICT
#<PACKAGE "COMMON-LISP-USER">
USE-PACKAGE
#<PACKAGE "EULER-UTIL">
EULER-UTIL:DIVISIBLE-BY
DIVISIBLE-BY)
Разрешение конфликта
Если это произойдет, вы можете решить эту проблему вручную. Здесь я использую SBCL в командной строке, но вы должны (я надеюсь) получить аналогичные параметры отладчика в SLIME. Для краткости я много вставляю в командную строку. Здесь важно следующее: --noinform
предотвращает печать баннера; --eval "'divisible-by"
проверяет наличие символа cl-user:divisible-by
; и --load file2.lisp
загружает ваш файл. То есть мы воссоздали проблему в командной строке, чтобы сосредоточиться на ее устранении.
$ sbcl --noinform --eval "'divisible-by" --load file2.lisp
debugger invoked on a NAME-CONFLICT in thread #<THREAD "initial thread" RUNNING
{1002979311}>:
USE-PACKAGE #<PACKAGE "EULER-UTIL"> causes name-conflicts in
#<PACKAGE "COMMON-LISP-USER"> between the following symbols:
EULER-UTIL:DIVISIBLE-BY, COMMON-LISP-USER::DIVISIBLE-BY
See also:
The ANSI Standard, Section 11.1.1.2.5
Type HELP for debugger help, or (SB-EXT:QUIT) to exit from SBCL.
restarts (invokable by number or by possibly-abbreviated name):
0: [RESOLVE-CONFLICT] Resolve conflict.
1: [RETRY ] Retry EVAL of current toplevel form.
2: [CONTINUE ] Ignore error and continue loading file "/home/taylorj/tmp/package-issue/file2.lisp".
3: [ABORT ] Abort loading file "/home/taylorj/tmp/package-issue/file2.lisp".
4: Ignore runtime option --load "file2.lisp".
5: Skip rest of --eval and --load options.
6: Skip to toplevel READ/EVAL/PRINT loop.
7: [QUIT ] Quit SBCL (calling #'QUIT, killing the process).
(NAME-CONFLICT
#<PACKAGE "COMMON-LISP-USER">
USE-PACKAGE
#<PACKAGE "EULER-UTIL">
EULER-UTIL:DIVISIBLE-BY
DIVISIBLE-BY)
Теперь вы можете ввести 0
, если хотите разрешить конфликт:
0] 0
Select a symbol to be made accessible in package COMMON-LISP-USER:
1. EULER-UTIL:DIVISIBLE-BY
2. COMMON-LISP-USER::DIVISIBLE-BY
Enter an integer (between 1 and 2): 1
Сделав euler-util:divisible-by
символ доступным в cl-user
, ваш код будет работать так, как вы ожидаете:
* (euler-1)
233168
Со свежим изображением проблем нет.
Хотя вы могли не вызвать проблему таким же образом, как я сделал выше, вероятно, что-то похожее. Похоже, вы загружаете код в не свежей среде (например, где вы уже ввели код, который заставил читателя интернировать "DIVISIBLE-BY"
в CL-USER
пакет. Со свежим Лиспом ваш код загружается нормально:
$ sbcl --load file2.lisp --noinform
* (euler-1)
233168
person
Joshua Taylor
schedule
24.02.2014
divisible-by
функции. - person Robert Harvey   schedule 25.02.2014use-package
компилируется, но эффектыuse-package
(функции, а не макроса) проявляются во время загрузки, а не во время компиляции. Таким образом, скомпилированный файл ссылается наcl-user::divisible-by
, и возникает конфликт имен после определения другого пакета. - person Joshua Taylor   schedule 25.02.2014