我正在使用基於CL的音樂作品的可視化編程環境。我試圖創建一個函數,當給定說3個元素(1 2 3)將返回1,2,3,1,2,3等,每次評估時的一個數字。這本書Common Lisp一個溫柔的介紹,簡單地提到可以使用尖銳的平等符號創建循環列表,但沒有詳細說明如何使用它們。請記住,我可以使用專門爲此設計的對象在程序中插入實際的Lisp代碼。Common Lisp中的圓形列表
回答
在Sharpsign Equal-Sign表示法中,它被寫爲#0=(1 2 3 . #0#)
。
下面是它創建從給定的參數,例如列表的功能:
(defun circular (first &rest rest)
(let ((items (cons first rest)))
(setf (cdr (last items)) items)))
然後調用將返回你想要的循環鏈表。只需使用car
和cdr
即可遍歷無限元素。
如果你真的想要一個迭代函數,它沒有參數和返回的下一個項目爲每個呼叫,這裏是你將如何做到這一點:
(defun make-iter (list)
(lambda()
(pop list)))
您可以使用PROG1而不是LET。 –
@ThomasBartscher謝謝!現已實施。 (其實我看着Rainer的回答,看起來'pop'和我之後做的事情是一樣的,當Schemer試圖寫CL的時候會發生什麼......-)) –
呵呵,我沒有想到這一點。太好了! –
CL-USER 3 > (defun circular (items)
(setf (cdr (last items)) items)
items)
CIRCULAR
CL-USER 4 > (setf *print-circle* t)
T
CL-USER 5 > (circular (list 1 2 3))
#1=(1 2 3 . #1#)
例子:
CL-USER 16 > (setf c1 (circular (list 1 2 3)))
#1=(1 2 3 . #1#)
CL-USER 17 > (pop c1)
1
CL-USER 18 > (pop c1)
2
CL-USER 19 > (pop c1)
3
CL-USER 20 > (pop c1)
1
也有:
CL-USER 6 > '#1=(1 2 3 . #1#)
#1=(1 2 3 . #1#)
添加了一點CLOS:
(defclass circular()
((items :initarg :items)))
(defmethod initialize-instance :after ((c circular) &rest initargs)
(setf (slot-value c 'items) (circular (slot-value c 'items))))
(defmethod next-item ((c circular))
(prog1 (first (slot-value c 'items))
(setf (slot-value c 'items)
(rest (slot-value c 'items)))))
CL-USER 7 > (setf circ1 (make-instance 'circular :items (list 1 2 3)))
#<CIRCULAR 40200017CB>
CL-USER 8 > (next-item circ1)
1
CL-USER 9 > (next-item circ1)
2
CL-USER 10 > (next-item circ1)
3
CL-USER 11 > (next-item circ1)
1
CL-USER 12 > (next-item circ1)
2
謝謝你,這是非常有幫助的。 –
是否有任何書籍或網站建議您幫助我瞭解更多關於此類事物的信息? –
在循環表達式上有一個放在Lambda上的部分:http://letoverlambda.com/index.cl/guest/chap4.html#sec_5 –
下面是Lisp中一個循環列表的一個想法。
;;; Showing structure of the list
;;; (next prev is-end val)
; create items
setf L-0 (L-1 L-3 t "L-0 sentry") ; this will be the sentry item so know where to stop
setf L-1 (L-2 L-0 nil "L-1")
setf L-2 (L-3 L-1 nil "L-2")
setf L-3 (L-0 L-2 nil "L-3")
; how to access L-2 from L-0
eval (first (eval (first L-0)))
; result: (L-3 L-1 NIL "L-2")
我沒有給予defun功能來添加,刪除和訪問項目。我在想,我給出的內容足以顯示你爲這種循環列表定義的任何函數所需做的事情。這似乎是我在聽衆中工作的。
- 1. 子列表Common Lisp中
- 2. 傳遞函數列表中的Common Lisp
- 3. Common Lisp的 - 在列表列出
- 4. Common Lisp中,列表處理(追加等)
- 5. Common Lisp從列表中創建矩陣
- 6. 在Common Lisp中合併列表項(Clisp)
- 7. 在Common Lisp中轉置列表
- 8. 轉換字符串列表Common Lisp中
- 9. 調用的函數Common Lisp的列表
- 10. Common Lisp中
- 11. 與Common Lisp中
- 12. 的#ifndef Common Lisp中
- 13. Common Lisp a Lisp-n?
- 14. 關於Common Lisp中
- 15. 規則Common Lisp中
- 16. 如果Common Lisp中
- 17. 如何Common Lisp中
- 18. 替換Common Lisp中
- 19. 如何在Common Lisp中打印列表爲矩陣列表
- 20. Common Lisp的Clojure中的PROGV
- 21. Common Lisp流?
- 22. Step Eval Common Lisp
- 23. 「unfold」for common lisp?
- 24. Predicates Common Lisp
- 25. Common Lisp SublimeREPL
- 26. Common Lisp Binary Tree
- 27. Scheme或Common Lisp?
- 28. common lisp和emacs
- 29. Common Lisp Loop Trouble
- 30. Common Lisp Timer
另請參見[Lisp循環列表](http://stackoverflow.com/q/15536564/1281433)和[Sharpsign等符號閱讀器宏示例](http://stackoverflow.com/q/12649290/1281433 )。 –