. navigate
Navigate
Query-IO    Page 34 left arrow
x
right arrow Page 36    Programming Environments
Query-IO








LISP Pointers
Volume I, Number 1
April-May 1987



Query-IO
page 35









Prev Article               Start of This Article               Next Article



Some old code looked like this:
    (progn
      (push new-item list-of-items)
      (delete old-item list-of-items) `
      list-of-items)
I changed it to:
    (progn
      (delete old-item list-of-items)
      (push new-item list-of-items)
      list-of-items)
  
Because delete works on a shorter list, it is likely to be faster. But now, sometimes old-item stays in list-of-items. What's wrong?



* * *


Dear Mighty,

Well, the macro call
(push new-item list-of-items)
is equivalent to
(setf list-of-items (cons new-item list-of-items)).
Therefore, it will update list-of-items correctly.

Delete is a destructive function meaning it can modify its argument but you cannot depend on it. During the function call, delete will locate the cons cell containing old-item, if it is not the first cons cell of list-of-items then it will "surgically" remove it from the list leaving list-of-items modified. However, if it is the first cons cell, delete will just return the cdr of list-of-items, leaving list-of-items unmodified.

The correct code is:
    (progn
      (setf list-of-items (delete old-item list-of-items))
      (push new-item list-of-items)
      list-of-items)
The moral is: don't count on destructive functions for doing the intended side effect on the arguments but use the result instead.

Oh, why did the old code work? I leave it to you.
Patrick.



Page Left left arrow         
x
right arrow Page Right
Vol. I, No. 1
Table of Contents




Home   Favorites   Computers   Map

IME logo Copyright © 2009, Mary S. Van Deusen