common-lisp
CLOSメタオブジェクトプロトコル
サーチ…
クラスのスロット名を取得する
私たちがクラスを持っているとしましょう
(defclass person ()
(name email age))
クラスのスロットの名前を取得するには、class-slots関数を使用します。これは、モップモップシステムによって提供されるモップモップパッケージにあります。実行中のlispイメージをロードするには(ql:quickload :closer-mop)
ます。クラススロットを呼び出す前にクラスがファイナライズされていることを確認する必要もあります。
(let ((class (find-class 'person)))
(c2mop:ensure-finalized class)
(c2mop:class-slots class))
有効なスロット定義オブジェクトのリストを返す:
(#<SB-MOP:STANDARD-EFFECTIVE-SLOT-DEFINITION S/TRANSFORMATIONS::NAME>
#<SB-MOP:STANDARD-EFFECTIVE-SLOT-DEFINITION S/TRANSFORMATIONS::EMAIL>
#<SB-MOP:STANDARD-EFFECTIVE-SLOT-DEFINITION S/TRANSFORMATIONS::AGE>)
別のスロットが変更されたときにスロットを更新する
CLOS MOPは、スロットが値にアクセス、読み取り、または変更されたときに呼び出されるフックスロット値使用クラスを提供します。このケースでは、変更を気にするだけなので、 (setf slot-value-using-class)
ためのメソッドを定義します。
(defclass document ()
((id :reader id :documentation "A hash computed with the contents of every other slot")
(title :initarg :title :accessor title)
(body :initarg :body :accessor body)))
(defmethod (setf c2mop:slot-value-using-class) :after
(new class (object document) (slot c2mop:standard-effective-slot-definition))
;; To avoid this method triggering a call to itself, we check that the slot
;; the modification occurred in is not the slot we are updating.
(unless (eq (slot-definition-name slot) 'id)
(setf (slot-value object 'id) (hash-slots object))))
インスタンス作成のslot-value
が呼び出されていないため、 initialize-instance :after
メソッドでコードを複製する必要があることに注意してください
(defmethod initialize-instance :after ((obj document) &key)
(setf (slot-value obj 'id)
(hash-slots obj)))
Modified text is an extract of the original Stack Overflow Documentation
ライセンスを受けた CC BY-SA 3.0
所属していない Stack Overflow