Skip to content

Instantly share code, notes, and snippets.

@kingcons
Last active December 14, 2015 02:59
Show Gist options
  • Save kingcons/5017627 to your computer and use it in GitHub Desktop.
Save kingcons/5017627 to your computer and use it in GitHub Desktop.
Best of both worlds.
(defmacro defenum (name (&rest keys))
"Define a function named %NAME, that takes an argument KEY. If KEYS are
scalar values, the corresponding index in KEYS is return. Otherwise, the
associated value is returned."
`(defun ,(intern (format nil "%~A" (string-upcase name))) (key)
(let ((enum ',(loop for i = 0 then (1+ i)
for key in keys
collect (typecase key
(list key)
(t (cons key i))))))
(rest (assoc key enum)))))
(defmacro defenum (name (&rest keys))
"Define a function named %NAME, that takes an argument KEY. If KEYS are
scalar values, the corresponding index in KEYS is return. Otherwise, the
associated value is returned."
(let* ((enum-sym (intern (format nil "*~A-ENUM*" (string-upcase name)))))
`(progn
(defvar ,enum-sym ',keys)
(defun ,(intern (format nil "%~A" (string-upcase name))) (key)
(position key ,enum-sym ,@(when (typep (car keys) 'list)
`(:key #'first)))))))
(defmacro defenum (name (&rest keys))
"Define a function named %NAME, that takes an argument KEY. If KEYS are
scalar values, the corresponding index in KEYS is return. Otherwise, the
associated value is returned."
`(defun ,(intern (format nil "%~A" (string-upcase name))) (key)
(let ((enum ',keys))
(position key enum ,@(when (typep (car keys) 'list) `(:key #'first))))))
;; Example Usage
(defenum status-bit (:carry :zero :interrupt :decimal
:break :unused :overflow :negative))
(defenum status-bit ((:carry 1) (:zero 2) (:interrupt 4) (:decimal 8)
(:break 16) (:unused 32) (:overflow 64) (:negative 128)))
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment