"Destructive" does not mean "operates in place". It means that the structure of the value operated on might be modified in some arbitrary and often undefined way. This can in some instances, implementations and cases have an effect as if it was "in place". This can generally not be relied upon, however.
If you use a destructive operator, you are telling the compiler that you are not interested in the previous value of the variable after the operation is complete. You should assume that that value is garbled beyond recognition afterwards and not use it anymore. Instead, you should use the return value of the operation.
(let ((a (list 1 2 3)))
(let ((b (delete 2 a)))
(frob b))
a)
=> You were eaten by a grue.
If you are unsure of the safety of destructive operations, use their non-destructive counterparts (remove
in this case).
(let ((a (list 1 2 3)))
(let ((b (remove 2 a)))
(frob b))
a)
=> (1 2 3)
If you really want to modify the contents of a variable, set them to the return value of the operation:
(let ((a (list 1 2 3)))
(setf a (delete 2 a))
a)
=> (1 3)