2017-11-30 6 views
3
나는이 목록에 점선 쌍 플립 SBCL이 노력하고있어

: 나는 (YMMV)이 얻을 그러나리스프 : psetf은 완전히 이해되지

(mapcar (lambda (x) (let ((num (random 2))) 
          (if (= num 0) 
          (psetf (cdr x) (car x) (car x) (cdr x)) 
          x))) 
       '((B . 21) (O . 24) (P . 15) (R . 47) (K . 49))) 

가 :

(NIL (O . 24) NIL (R . 47) (K . 49)) 

을 알려줍니다 psetf 님은 내가 무엇을하고 있는지에 대해 관심이 없습니다. 알다시피, psetf은 파괴적이며 NIL을 반환합니다. 나는 여기서 무엇을 이해하지 못 하겠는가?

답변

9

당신이 관찰 동작은 정확하고 예상이다 num이 0 인 경우 psetf 반환 nilmapcar 장소 반환 목록에 반환 값 , 그래서, 당신이 거기 nil, 를 얻을이 1 일 때, 당신은 얻을 원래의 세포.

가 쉽게 고정 :

(mapcar (lambda (x) 
      (when (zerop (random 2)) 
      (psetf (cdr x) (car x) (car x) (cdr x))) 
      x) 
     '((B . 21) (O . 24) (P . 15) (R . 47) (K . 49))) 
==> ((B . 21) (24 . O) (P . 15) (47 . R) (K . 49)) 

실제로, CL은이 rotatef 매크로 당신의 사건에 대한 :

(mapcar (lambda (x) 
      (when (zerop (random 2)) 
      (rotatef (cdr x) (car x))) 
      x) 
     '((B . 21) (O . 24) (P . 15) (R . 47) (K . 49))) 
==> ((21 . B) (O . 24) (15 . P) (R . 47) (K . 49)) 

마지막으로,주의하시기 바랍니다 modifying quoted data is a very bad idea 그 :

(defparameter *alist-0* '((B . 21) (O . 24) (P . 15) (R . 47) (K . 49))) 
(defparameter *alist-1* 
    (mapcar (lambda (x) 
      (when (zerop (random 2)) 
       (rotatef (cdr x) (car x))) 
      x) 
      *alist-0*)) 
(eq *alist-0* *alist-1*) 
==> nil 
(equal *alist-0* *alist-1*) 
==> t ; !!! 
(every #'eq *alist-0* *alist-1*) 
==> t 

즉, 세포는 동일하지만 목록은 다르다. nt.

아마 지속적으로 모든 셀을 복사 좋을 것이다 :

(defparameter *alist-2* 
    (mapcar (lambda (x) 
      (if (zerop (random 2)) 
       (cons (cdr x) (car x)) 
       (cons (car x) (cdr x)))) 
      *alist-0*)) 
*alist-0* 
==> ((B . 21) (O . 24) (P . 15) (R . 47) (K . 49)) 
*alist-2* 
==> ((21 . B) (O . 24) (15 . P) (R . 47) (K . 49)) 
3

종종 하나는 단점 세포를 수정하지 않도록 할 수 있습니다. cons 새로운 것들.

CL-USER 76 > (mapcar (lambda (pair) 
         (if (= (random 2) 0) 
          (cons (cdr pair) 
           (car pair)) 
         pair)) 
        '((B . 21) (O . 24) (P . 15) (R . 47) (K . 49))) 
((21 . B) (24 . O) (P . 15) (47 . R) (49 . K)) 
+0

결과에있는 일부 단점 셀은 인용 된 데이터에서 나온 것입니다. – sds