emacs:符号的函数定义无效:循环
emacs: Symbol's function definition is void: loop
我正在测试在 emacs init.el
(Emacs 24.3) 中加载包。我跟着emacs prelude
的作者a blog 自动加载包,把那里的代码复制到我的init.el
下面。但是,我收到一条关于 loop
function/symbol 的错误消息,上面写着:
Symbol's function definition is void: loop
有人可以解释一下如何修复代码吗?
在网上查了一下,好像loop
是cl-lib
里面的一个宏。我的猜测是缺少 loop
的定义,我试图通过添加 (require 'cl-lib)
来解决问题,如代码所示,但错误仍然存在。还有其他关于类似错误消息的 SO 问题,例如:ELisp: cl-loop for "Symbol's value as variable is void", Symbol's function definition is void: declare-function。但是错误消息在缺少什么方面有所不同,答案大多建议替代路线,例如使用更新版本的 emacs。
-- 代码--
(require 'package)
(add-to-list 'package-archives
'("melpa-stable" . "http://stable.melpa.org/packages/") t)
(package-initialize)
;;; check & load packages
(defvar prelude-packages
'( haskell-mode )
"A list of packages to ensure are installed at launch.")
;;(require 'cl-lib) ;debug
(defun prelude-packages-installed-p ()
(loop for p in prelude-packages
when (not (package-installed-p p)) do (return nil)
finally (return t)))
(unless (prelude-packages-installed-p)
;; check for new packages (package versions)
(message "%s" "Emacs Prelude is now refreshing its package database...")
(package-refresh-contents)
(message "%s" " done.")
;; install the missing packages
(dolist (p prelude-packages)
(when (not (package-installed-p p))
(package-install p))))
(provide 'prelude-packages)
;;; end load packages
cl-lib
包是在 Emacs 24.3 中引入的,它提供了许多 Common Lisp 功能,所有功能都带有 cl-
前缀。在此之前,使用这些功能的唯一方法是需要 cl
库,并使用无前缀的名称,例如loop
而不是 cl-loop
。但是,由于可能存在名称冲突,因此不鼓励这样做,通常建议尽可能使用前缀名称。
由于您使用的是 Emacs 24.3,解决此问题的 "correct" 方法是将 loop
替换为 cl-loop
并将 return
替换为 cl-return
:
(defun prelude-packages-installed-p ()
(cl-loop for p in prelude-packages
when (not (package-installed-p p)) do (cl-return nil)
finally (cl-return t)))
(您不需要 (require 'cl-lib)
,因为 cl-loop
和 cl-return
是自动加载的。)
或者,您可以添加 (require 'cl)
以访问无前缀的名称,并保持代码不变。这也适用于早期的 Emacs 版本。
我不禁注意到这个函数可以写得更简洁:
(defun prelude-packages-installed-p ()
(cl-every 'package-installed-p prelude-packages))
关于 cl-every
加 cl-lib
与 every
加 cl
的相同问题适用。
我正在测试在 emacs init.el
(Emacs 24.3) 中加载包。我跟着emacs prelude
的作者a blog 自动加载包,把那里的代码复制到我的init.el
下面。但是,我收到一条关于 loop
function/symbol 的错误消息,上面写着:
Symbol's function definition is void: loop
有人可以解释一下如何修复代码吗?
在网上查了一下,好像loop
是cl-lib
里面的一个宏。我的猜测是缺少 loop
的定义,我试图通过添加 (require 'cl-lib)
来解决问题,如代码所示,但错误仍然存在。还有其他关于类似错误消息的 SO 问题,例如:ELisp: cl-loop for "Symbol's value as variable is void", Symbol's function definition is void: declare-function。但是错误消息在缺少什么方面有所不同,答案大多建议替代路线,例如使用更新版本的 emacs。
-- 代码--
(require 'package)
(add-to-list 'package-archives
'("melpa-stable" . "http://stable.melpa.org/packages/") t)
(package-initialize)
;;; check & load packages
(defvar prelude-packages
'( haskell-mode )
"A list of packages to ensure are installed at launch.")
;;(require 'cl-lib) ;debug
(defun prelude-packages-installed-p ()
(loop for p in prelude-packages
when (not (package-installed-p p)) do (return nil)
finally (return t)))
(unless (prelude-packages-installed-p)
;; check for new packages (package versions)
(message "%s" "Emacs Prelude is now refreshing its package database...")
(package-refresh-contents)
(message "%s" " done.")
;; install the missing packages
(dolist (p prelude-packages)
(when (not (package-installed-p p))
(package-install p))))
(provide 'prelude-packages)
;;; end load packages
cl-lib
包是在 Emacs 24.3 中引入的,它提供了许多 Common Lisp 功能,所有功能都带有 cl-
前缀。在此之前,使用这些功能的唯一方法是需要 cl
库,并使用无前缀的名称,例如loop
而不是 cl-loop
。但是,由于可能存在名称冲突,因此不鼓励这样做,通常建议尽可能使用前缀名称。
由于您使用的是 Emacs 24.3,解决此问题的 "correct" 方法是将 loop
替换为 cl-loop
并将 return
替换为 cl-return
:
(defun prelude-packages-installed-p ()
(cl-loop for p in prelude-packages
when (not (package-installed-p p)) do (cl-return nil)
finally (cl-return t)))
(您不需要 (require 'cl-lib)
,因为 cl-loop
和 cl-return
是自动加载的。)
或者,您可以添加 (require 'cl)
以访问无前缀的名称,并保持代码不变。这也适用于早期的 Emacs 版本。
我不禁注意到这个函数可以写得更简洁:
(defun prelude-packages-installed-p ()
(cl-every 'package-installed-p prelude-packages))
关于 cl-every
加 cl-lib
与 every
加 cl
的相同问题适用。