mirror of
https://git.savannah.gnu.org/git/emacs.git
synced 2024-12-23 10:34:07 +00:00
Improve mutability documentation
This change was inspired by comments from Štěpán Němec in: https://lists.gnu.org/r/emacs-devel/2020-04/msg01063.html * doc/lispref/objects.texi (Lisp Data Types): Mention mutability. (Constants and mutability): New section. * doc/lispintro/emacs-lisp-intro.texi (Lists diagrammed) (Indent Tabs Mode): Improve wording. * doc/lispref/eval.texi (Self-Evaluating Forms): Say that they return constants. * doc/lispref/lists.texi (Sets And Lists): Fix memql mistake/confusion that I recently introduced.
This commit is contained in:
parent
81e7d7f111
commit
dca35b31d0
@ -9557,7 +9557,7 @@ part of which is the address of the next pair. The very last box
|
||||
points to the symbol @code{nil}, which marks the end of the list.
|
||||
|
||||
@need 1200
|
||||
When a variable is set to a list via @code{setq},
|
||||
When a variable is set to a list with an operation such as @code{setq},
|
||||
it stores the address of the first box in the variable. Thus,
|
||||
evaluation of the expression
|
||||
|
||||
@ -17140,7 +17140,7 @@ The following turns off Indent Tabs mode:
|
||||
@end smallexample
|
||||
|
||||
Note that this line uses @code{setq-default} rather than the
|
||||
@code{setq} that we have seen before. The @code{setq-default}
|
||||
@code{setq} that we have seen before; @code{setq-default}
|
||||
sets values only in buffers that do not have their own local
|
||||
values for the variable.
|
||||
|
||||
|
@ -297,6 +297,7 @@ Lisp Data Types
|
||||
* Circular Objects:: Read syntax for circular structure.
|
||||
* Type Predicates:: Tests related to types.
|
||||
* Equality Predicates:: Tests of equality between any two objects.
|
||||
* Constants and Mutability:: Whether an object's value can change.
|
||||
|
||||
Programming Types
|
||||
|
||||
|
@ -158,6 +158,12 @@ contents unchanged.
|
||||
@end group
|
||||
@end example
|
||||
|
||||
A self-evaluating form yields a constant, and you should not attempt
|
||||
to modify the constant's contents via @code{setcar}, @code{aset} or
|
||||
similar primitives. The Lisp interpreter might unify the constants
|
||||
yielded by your program's self-evaluating forms, so that these
|
||||
constants might share structure. @xref{Constants and Mutability}.
|
||||
|
||||
It is common to write numbers, characters, strings, and even vectors
|
||||
in Lisp code, taking advantage of the fact that they self-evaluate.
|
||||
However, it is quite unusual to do this for types that lack a read
|
||||
@ -559,6 +565,7 @@ and vectors.)
|
||||
@defspec quote object
|
||||
This special form returns @var{object}, without evaluating it.
|
||||
The returned value is a constant, and should not be modified.
|
||||
@xref{Constants and Mutability}.
|
||||
@end defspec
|
||||
|
||||
@cindex @samp{'} for quoting
|
||||
|
@ -866,16 +866,15 @@ foo ;; @r{@code{foo} was changed.}
|
||||
@node Modifying Lists
|
||||
@section Modifying Existing List Structure
|
||||
@cindex destructive list operations
|
||||
@cindex constant lists
|
||||
@cindex mutable lists
|
||||
|
||||
You can modify the @sc{car} and @sc{cdr} contents of a cons cell with the
|
||||
primitives @code{setcar} and @code{setcdr}. These are destructive
|
||||
operations because they change existing list structure.
|
||||
Destructive operations should be applied only to @dfn{mutable} lists,
|
||||
Destructive operations should be applied only to mutable lists,
|
||||
that is, lists constructed via @code{cons}, @code{list} or similar
|
||||
operations. Lists created by quoting are constants and should not be
|
||||
changed by destructive operations.
|
||||
changed by destructive operations. @xref{Constants and Mutability}.
|
||||
|
||||
@cindex CL note---@code{rplaca} vs @code{setcar}
|
||||
@quotation
|
||||
@ -1169,9 +1168,9 @@ x
|
||||
@end group
|
||||
@end example
|
||||
|
||||
However, the other arguments (all but the last) must be mutable lists.
|
||||
However, the other arguments (all but the last) should be mutable lists.
|
||||
|
||||
A common pitfall is to use a quoted constant list as a non-last
|
||||
A common pitfall is to use a constant list as a non-last
|
||||
argument to @code{nconc}. If you do this, the resulting behavior
|
||||
is undefined. It is possible that your program will change
|
||||
each time you run it! Here is what might happen (though this
|
||||
@ -1359,12 +1358,12 @@ Compare this with @code{memq}:
|
||||
|
||||
@example
|
||||
@group
|
||||
(memql 1.2 '(1.1 1.2 1.3)) ; @r{@code{1.2} and @code{1.2} are @code{eql}.}
|
||||
(memql 1.2 '(1.1 1.2 1.3)) ; @r{@code{1.2} and @code{1.2} must be @code{eql}.}
|
||||
@result{} (1.2 1.3)
|
||||
@end group
|
||||
@group
|
||||
(memq (list 2) '((1) (2))) ; @r{@code{(list 2)} and @code{(2)} are not @code{eq}.}
|
||||
@result{} nil
|
||||
(memq 1.2 '(1.1 1.2 1.3)) ; @r{@code{1.2} and @code{1.2} need not be @code{eq}.}
|
||||
@result{} nil ; @r{... or it might be @code{(1.2 1.3)}.}
|
||||
@end group
|
||||
@end example
|
||||
@end defun
|
||||
@ -1628,6 +1627,7 @@ keys may not be symbols:
|
||||
'(("simple leaves" . oak)
|
||||
("compound leaves" . horsechestnut)))
|
||||
|
||||
;; @r{The @code{copy-sequence} means the keys are not @code{eq}.}
|
||||
(assq (copy-sequence "simple leaves") leaves)
|
||||
@result{} nil
|
||||
(assoc (copy-sequence "simple leaves") leaves)
|
||||
|
@ -46,6 +46,10 @@ you store in it, type and all. (Actually, a small number of Emacs
|
||||
Lisp variables can only take on values of a certain type.
|
||||
@xref{Variables with Restricted Values}.)
|
||||
|
||||
Some Lisp objects are @dfn{constant}: their values never change.
|
||||
Others are @dfn{mutable}: their values can be changed via destructive
|
||||
operations that involve side effects.
|
||||
|
||||
This chapter describes the purpose, printed representation, and read
|
||||
syntax of each of the standard types in GNU Emacs Lisp. Details on how
|
||||
to use these types can be found in later chapters.
|
||||
@ -59,6 +63,7 @@ to use these types can be found in later chapters.
|
||||
* Circular Objects:: Read syntax for circular structure.
|
||||
* Type Predicates:: Tests related to types.
|
||||
* Equality Predicates:: Tests of equality between any two objects.
|
||||
* Constants and Mutability:: Whether an object's value can change.
|
||||
@end menu
|
||||
|
||||
@node Printed Representation
|
||||
@ -2373,3 +2378,43 @@ that for two strings to be equal, they have the same text properties.
|
||||
@end group
|
||||
@end example
|
||||
@end defun
|
||||
|
||||
@node Constants and Mutability
|
||||
@section Constants and Mutability
|
||||
@cindex constants
|
||||
@cindex mutable objects
|
||||
|
||||
Some Lisp objects are constant: their values never change.
|
||||
For example, you can create a new integer by calculating one, but you
|
||||
cannot modify the value of an existing integer.
|
||||
|
||||
Other Lisp objects are mutable: their values can be changed
|
||||
via destructive operations involving side effects. For example, an
|
||||
existing marker can be changed by moving the marker to point to
|
||||
somewhere else.
|
||||
|
||||
Although numbers are always constants and markers are always
|
||||
mutable, some types contain both constant and mutable members. These
|
||||
types include conses, vectors, and strings. For example, the string
|
||||
literal @code{"aaa"} yields a constant string, whereas the function
|
||||
call @code{(make-string 3 ?a)} yields a mutable string that can be
|
||||
changed via later calls to @code{aset}.
|
||||
|
||||
A program should not attempt to modify a constant because the
|
||||
resulting behavior is undefined: the Lisp interpreter might or might
|
||||
not detect the error, and if it does not detect the error the
|
||||
interpreter can behave unpredictably thereafter. Another way to put
|
||||
this is that mutable objects are safe to change, whereas constants are
|
||||
not safely mutable: if you try to change a constant your program might
|
||||
behave as you expect but it might crash or worse. This problem occurs
|
||||
with types that have both constant and mutable members, and that have
|
||||
mutators like @code{setcar} and @code{aset} that are valid on mutable
|
||||
objects but hazardous on constants.
|
||||
|
||||
When the same constant occurs multiple times in a program, the Lisp
|
||||
interpreter might save time or space by reusing existing constants or
|
||||
constant components. For example, @code{(eq "abc" "abc")} returns
|
||||
@code{t} if the interpreter creates only one instance of the string
|
||||
constant @code{"abc"}, and returns @code{nil} if it creates two
|
||||
instances. Lisp programs should be written so that they work
|
||||
regardless of whether this optimization is in use.
|
||||
|
@ -1249,7 +1249,7 @@ x
|
||||
|
||||
The @var{array} should be mutable; that is, it should not be a constant,
|
||||
such as the constants created via quoting or via self-evaluating forms.
|
||||
@xref{Self-Evaluating Forms}.
|
||||
@xref{Constants and Mutability}.
|
||||
|
||||
If @var{array} is a string and @var{object} is not a character, a
|
||||
@code{wrong-type-argument} error results. The function converts a
|
||||
@ -1306,10 +1306,10 @@ same way in Lisp input.
|
||||
|
||||
A vector, like a string or a number, is considered a constant for
|
||||
evaluation: the result of evaluating it is the same vector. This does
|
||||
not evaluate or even examine the elements of the vector. Vectors
|
||||
written with square brackets are constants and should not be modified
|
||||
via @code{aset} or other destructive operations.
|
||||
@xref{Self-Evaluating Forms}.
|
||||
not evaluate or even examine the elements of the vector.
|
||||
@xref{Self-Evaluating Forms}. Vectors written with square brackets
|
||||
are constants and should not be modified via @code{aset} or other
|
||||
destructive operations. @xref{Constants and Mutability}.
|
||||
|
||||
Here are examples illustrating these principles:
|
||||
|
||||
|
@ -384,6 +384,7 @@ usual value is @w{@code{"[ \f\t\n\r\v]+"}}.
|
||||
You can alter the contents of a mutable string via operations
|
||||
described in this section. However, you should not try to use these
|
||||
operations to alter the contents of a constant string.
|
||||
@xref{Constants and Mutability}.
|
||||
|
||||
The most basic way to alter the contents of an existing string is with
|
||||
@code{aset} (@pxref{Array Functions}). @code{(aset @var{string}
|
||||
|
Loading…
Reference in New Issue
Block a user