[ < ] | [ > ] | [ << ] | [ Up ] | [ >> ] | [Top] | [Contents] | [Index] | [ ? ] |
Common Lisp includes a complex and powerful “declaration”
mechanism that allows you to give the compiler special hints
about the types of data that will be stored in particular variables,
and about the ways those variables and functions will be used. This
package defines versions of all the Common Lisp declaration forms:
declare
, locally
, proclaim
, declaim
,
and the
.
Most of the Common Lisp declarations are not currently useful in
Emacs Lisp, as the byte-code system provides little opportunity
to benefit from type information, and special
declarations
are redundant in a fully dynamically-scoped Lisp. A few
declarations are meaningful when the optimizing Emacs 19 byte
compiler is being used, however. Under the earlier non-optimizing
compiler, these declarations will effectively be ignored.
This function records a “global” declaration specified by
decl-spec. Since proclaim
is a function, decl-spec
is evaluated and thus should normally be quoted.
This macro is like proclaim
, except that it takes any number
of decl-spec arguments, and the arguments are unevaluated and
unquoted. The declaim
macro also puts an (eval-when
(compile load eval) ...)
around the declarations so that they will
be registered at compile-time as well as at run-time. (This is vital,
since normally the declarations are meant to influence the way the
compiler treats the rest of the file that contains the declaim
form.)
This macro is used to make declarations within functions and other
code. Common Lisp allows declarations in various locations, generally
at the beginning of any of the many “implicit progn
s”
throughout Lisp syntax, such as function bodies, let
bodies,
etc. Currently the only declaration understood by declare
is special
.
In this package, locally
is no different from progn
.
Type information provided by the
is ignored in this package;
in other words, (the type form)
is equivalent
to form. Future versions of the optimizing byte-compiler may
make use of this information.
For example, mapcar
can map over both lists and arrays. It is
hard for the compiler to expand mapcar
into an in-line loop
unless it knows whether the sequence will be a list or an array ahead
of time. With (mapcar 'car (the vector foo))
, a future
compiler would have enough information to expand the loop in-line.
For now, Emacs Lisp will treat the above code as exactly equivalent
to (mapcar 'car foo)
.
Each decl-spec in a proclaim
, declaim
, or
declare
should be a list beginning with a symbol that says
what kind of declaration it is. This package currently understands
special
, inline
, notinline
, optimize
,
and warn
declarations. (The warn
declaration is an
extension of standard Common Lisp.) Other Common Lisp declarations,
such as type
and ftype
, are silently ignored.
special
Since all variables in Emacs Lisp are “special” (in the Common
Lisp sense), special
declarations are only advisory. They
simply tell the optimizing byte compiler that the specified
variables are intentionally being referred to without being
bound in the body of the function. The compiler normally emits
warnings for such references, since they could be typographical
errors for references to local variables.
The declaration (declare (special var1 var2))
is
equivalent to (defvar var1) (defvar var2)
in the
optimizing compiler, or to nothing at all in older compilers (which
do not warn for non-local references).
In top-level contexts, it is generally better to write
(defvar var)
than (declaim (special var))
,
since defvar
makes your intentions clearer. But the older
byte compilers can not handle defvar
s appearing inside of
functions, while (declare (special var))
takes care
to work correctly with all compilers.
inline
The inline
decl-spec lists one or more functions
whose bodies should be expanded “in-line” into calling functions
whenever the compiler is able to arrange for it. For example,
the Common Lisp function cadr
is declared inline
by this package so that the form (cadr x)
will
expand directly into (car (cdr x))
when it is called
in user functions, for a savings of one (relatively expensive)
function call.
The following declarations are all equivalent. Note that the
defsubst
form is a convenient way to define a function
and declare it inline all at once, but it is available only in
Emacs 19.
(declaim (inline foo bar)) (eval-when (compile load eval) (proclaim '(inline foo bar))) (proclaim-inline foo bar) ; XEmacs only (defsubst foo (...) ...) ; instead of defun; Emacs 19 only |
Please note: This declaration remains in effect after the containing source file is done. It is correct to use it to request that a function you have defined should be inlined, but it is impolite to use it to request inlining of an external function.
In Common Lisp, it is possible to use (declare (inline …))
before a particular call to a function to cause just that call to
be inlined; the current byte compilers provide no way to implement
this, so (declare (inline …))
is currently ignored by
this package.
notinline
The notinline
declaration lists functions which should
not be inlined after all; it cancels a previous inline
declaration.
optimize
This declaration controls how much optimization is performed by the compiler. Naturally, it is ignored by the earlier non-optimizing compilers.
The word optimize
is followed by any number of lists like
(speed 3)
or (safety 2)
. Common Lisp defines several
optimization “qualities”; this package ignores all but speed
and safety
. The value of a quality should be an integer from
0 to 3, with 0 meaning “unimportant” and 3 meaning “very important.”
The default level for both qualities is 1.
In this package, with the Emacs 19 optimizing compiler, the
speed
quality is tied to the byte-compile-optimize
flag, which is set to nil
for (speed 0)
and to
t
for higher settings; and the safety
quality is
tied to the byte-compile-delete-errors
flag, which is
set to t
for (safety 3)
and to nil
for all
lower settings. (The latter flag controls whether the compiler
is allowed to optimize out code whose only side-effect could
be to signal an error, e.g., rewriting (progn foo bar)
to
bar
when it is not known whether foo
will be bound
at run-time.)
Note that even compiling with (safety 0)
, the Emacs
byte-code system provides sufficient checking to prevent real
harm from being done. For example, barring serious bugs in
Emacs itself, Emacs will not crash with a segmentation fault
just because of an error in a fully-optimized Lisp program.
The optimize
declaration is normally used in a top-level
proclaim
or declaim
in a file; Common Lisp allows
it to be used with declare
to set the level of optimization
locally for a given form, but this will not work correctly with the
current version of the optimizing compiler. (The declare
will set the new optimization level, but that level will not
automatically be unset after the enclosing form is done.)
warn
This declaration controls what sorts of warnings are generated
by the byte compiler. Again, only the optimizing compiler
generates warnings. The word warn
is followed by any
number of “warning qualities,” similar in form to optimization
qualities. The currently supported warning types are
redefine
, callargs
, unresolved
, and
free-vars
; in the current system, a value of 0 will
disable these warnings and any higher value will enable them.
See the documentation for the optimizing byte compiler for details.
[ << ] | [ >> ] | [Top] | [Contents] | [Index] | [ ? ] |
This document was generated by Aidan Kehoe on December 27, 2016 using texi2html 1.82.