help-gnu-emacs
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: Always return a list


From: Pascal J. Bourguignon
Subject: Re: Always return a list
Date: Fri, 26 Nov 2010 01:24:57 +0100
User-agent: Gnus/5.13 (Gnus v5.13) Emacs/23.2 (gnu/linux)

Johan Andersson <johan.rejeep@gmail.com> writes:

> Hey,
>
> I have a struct. To make it simple, lets assume this is the struct:
>   (defstruct package name deps)
>
> The deps slot is for the package dependencies. Example of packages:
>   (make-package :name "one" :deps "two")
>   (make-package :name "two" :deps '("three" "four"))
>
> To make it easier to use the dependencies from the code, when I call 
> (package-deps package) I always want it to return a list. So:
>
>   (let ((one (make-package :name "one" :deps "two"))
>         (two (make-package :name "two" :deps '("three" "four"))))
>
>     (print (package-deps one)) ;; => ("two")
>     (print (package-deps two)) ;; => ("three" "four")
>     )
>
> I tried doing this using an advice, with no success:
>   (defadvice package-deps (around package-deps-around)
>     (let ((deps ad-do-it))
>       (if (listp deps) deps (list deps))))
>   (ad-activate 'package-deps)
>
> Can I do this in a way that doesn't require that much of a hack?


defstruct is a good macro.  There's no reason why not to use it.

My advice is to always store a list.  If you want the convenience of
initializing the structure without a list, you can write your own
constructor:

(require 'cl) ; as always.  Put this require in your ~/.emacs

(defstruct (package (:constructor %make-package)) 
   (name "unnamed" :type string)
   (deps '()       :type list))

(defun* make-package (&key name deps)
  (%make-package :name name :deps (ensure-list deps)))

(package-deps (make-package :name "one"))                        --> nil
(package-deps (make-package :name "one" :deps "two"))            --> ("two")
(package-deps (make-package :name "one" :deps '("two" "three"))) --> ("two" 
"three")


Of course ensure-list is a library function.  If you don't already have
a library with it, here it is:

(defun ensure-list (x) (if (listp x) x (list x)))



-- 
__Pascal Bourguignon__                     http://www.informatimago.com/
A bad day in () is better than a good day in {}.


reply via email to

[Prev in Thread] Current Thread [Next in Thread]