Cố gắng hiểu những gì setf
có thể làm, tôi gọi
(macroexpand '(setf (aref vec i) val))
⇒ (let* ((v vec) (v i)) (aset v v val))
Điều này rõ ràng là sai.
Tuy nhiên tôi không thể tạo ra một ví dụ thực tế khi (setf (aref ..
thất bại. Ví dụ
(setq vec (make-vector 10 nil) i 3 val 'foo)
⇒ foo
(setf (aref vec i) val)
⇒ foo
vec
⇒ [nil nil nil foo nil nil nil nil nil nil]
Ai đó có thể giải thích những gì đang xảy ra ở đây?
Kỳ lạ thay, các mã cho
—
PHS
setf
trong tập tin nguồn gv.el
dường như để tạo ra các v
biểu tượng với một sử dụng vani của (gensym "v")
và điều này nên nối thêm một giá trị truy cập sau "v" tiền tố, tạo ra những biểu tượng uninterned v0
, v1
, v2
vv
Bạn có thể muốn chơi với
—
Stefan
print-gensym
để thấy rõ hơn những gì đang diễn ra.
@stefan: Tôi có emacs-26.1 và nó không có
—
phs
print-gensym
AFAICT :-( Có ai có lời giải thích tại sao (gensym "v")
tệp trong nguồn gv.el
không xuất hiện không gensym-counter
?!
Tôi khá chắc chắn rằng bạn có
—
Stefan
print-gensym
, bạn có thể chỉ nhìn nhầm chỗ (thử C-h o
thay vì C-h f
). Các let*
trong mã mở rộng của bạn có khả năng tạo ra bởi macroexp-let2
đó sử dụng make-symbol
chứ không phải là gensym
.
v
biểu tượng không giống nhau và(let* ((form (macroexpand '(setf (aref vec i) val))) (symb1 (caar (cadr form))) (symb2 (caar (cdadr form)))) (equal symb1 symb2))
trả vềnil
.