Does a setfable nthcdr implementation exist?

谁说我不能喝 提交于 2019-12-10 03:38:49

问题


I am using clisp and I wonder if there is any library with a setfable version of nthcdr that I can use.


回答1:


You can hack around it with:

(let ((lst (list 1 2 3 4))
      (n 2))
  (setf (cdr (nthcdr (1- n) lst)) '(5 6 7))
  l)
> (1 2 5 6 7)

Or define your own setf for it:

;; !!warning!!  only an example, lots of nasty edge cases
(defsetf nthcdr (n lst) (new-val) 
   `(setf (cdr (nthcdr (1- ,n) ,lst)) ,new-val))

I do not know why nthcdr does not have a setf defined. Even Alexandria seems to define setf for last, but not nthcdr.

PS. I would treat wanting to setf an nthcdr as a bad smell in your code.




回答2:


(defsetf my-nthcdr (n list) (store)
  (let ((tmp (gensym)))
    `(let ((,tmp (nthcdr (1- ,n) ,list)))
       (rplacd ,tmp ,store)
       (cdr ,tmp))))

Doesn't work when n is 0 though, you could make it work when LIST is a symbol, checking if N is zero either on macroexpansion time, but then it only works if N is a number, or including the check in the expanded code.



来源:https://stackoverflow.com/questions/4387967/does-a-setfable-nthcdr-implementation-exist

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!