almost 4 years ago

А вы знали, что в качестве ключа хэш-таблицы в Common Lisp можно использовать любые объекты?

Например, так:

(defparameter *table* (make-hash-table :test #'equal))

; voila: lists
(setf (gethash '(abcde 12345) *table*) 2)

(defclass point ()
  ((x :initarg x) (y :initarg y)))

;voila: objects (!!)
(setf (gethash (make-instance 'point 'x 1 'y 2) *table*) 44)

После этого делаем:

(loop for key being each hash-key of *table* using (hash-value value) 
  doing (format T "~a: ~a~%" key value))

Результат:

(ABCDE 12345): 2
#<POINT #x302000EEB56D>: 44
NIL

Однако, следует учесть, что хотя перечисление элементов и работает на объектах, gethash не найдёт нам элемент по ключу-объекту:

(gethash '(abcde 12345) *table*) => 2 T
(gethash (make-instance 'point 'x 1 'y 2) *table*) => NIL NIL

Так что любой элемент данных, который матчится в самом общем случае по equalp, может теоретически быть использован как ключ в хэш-таблице. По-моему, это просто офигительно.

 
comments powered by Disqus