[Gsll-devel] About the naming convention in gsll

Liam Healy lhealy at common-lisp.net
Fri May 16 21:02:18 UTC 2008


My naming scheme was somewhat arbitrary, but I was attempting
to use "normal" names, rather than truncated C-like names with
boilerplate identifiers prepended (like gsl_).   I am certainly
amenable to changing it, but I think Zach's suggestion about
packages is what I intended: you shouldn't really program in
the GSLL package; make your own package like gsll-user and
you can do whatever you want.

But the larger question is what are the "usable" functions.
GSLL is fairly low-level now, of necessity.  You have to start
somewhere in building a lisp-natural interface, and it was
necessary to get it good enough to be usable and to
establish the common definitions that it could be put out
for others to join in and work on higher level interfaces.

So I'm willing to change things, certainly.  However, the example
you gave I am not sympathetic to; you don't like GSLL taking
#'solve-tridiagonal because you do a mass copying of arrays
and you want that mandatory and built-in.
I don't think copying should be part of the library call because
the user is compelled to pay a copying penalty which may
(and should) be minimized by working in foreign arrays throughout
the computation.   What if the array came from another GSLL
calculation; would you build in a copying to CL at the end and then
copy it back to C?  What if there were several, or
several thousand, such chained calculations?  There were some
spots where I struggled with whether to copy or not; in some cases
it copies but in places where I felt chaining was likely it does not.

As a side point, I am working on incorporating
foreign-friendly arrays, and there is a separate function
(currently called make-array*) that creates arrays, similar to
make-array, but the type specification is mandatory.  If
you are using SBCL, the C array is the CL array;
if not, the right thing will always happen (once debugged...).

I am unclear on what the point of the macro is; if it were a function
it would do the same thing.  There is no passing by value in any case
as far as I know; do you mean a copying of arrays?  You're
going to get that anyway; there's no way to avoid it in ANSI standard
CL.

Liam




On Fri, May 16, 2008 at 4:28 PM, Mirko Vukovic <mirko.vukovic at gmail.com> wrote:
> On Fri, May 16, 2008 at 3:20 PM, Zach <elzacho at gmail.com> wrote:
>> Mirko,
>>
>> I am in the same boat as you as I have rarely used GSLL for anything.
>
> I hope to use it more for numerics and data analysis, within nlisp.
> But I am (even after a few months) just starting with lisp, and my
> synapses are still lacking.
>
>>
>> However, name conflicts in CL can be dealt with by the package system,
>> right?  As in,
>>
>> (defpackage :gsll-wrapper
>>   (:use :cl)
>>   (:export #:letm #:vector-double-float #:data
>>               ;; And the rest of the GSLL names you like
>>               )
>>   (:shadow #:solve-tridiagonal) ) ; shadow GSLL's function and replace it
>>
>> (in-package :gsll-wrapper)
>>
>> ;; Define your SOLVE-TRIDIAGONAL
>> (defun solve-tridiagonal (args*)
>>   your definition ...
>>   (gsll:solve-tridiagonal ...)
>>   more stuff ... )
>
> Your suggestion seems very sensible.
>
>>
>> Then, just use your custom wrapped version of GSLL instead.
>>
>> Perhaps I am wrong, but it seems that GSLL is shaping up to be a relatively
>> low level binding to GSL.  Luckily, the issue you raise is easily
>> corrected.  In my opinion, you are right that much work can be done in the
>> direction of abstracting away the foreign feel of GSLL.
>
> That seems correct.  That is why I felt that the functions generated
> by GSLL should correspond closely to GSLL names, since they are
> essentially wrappers.  One would hope that with time, there would be a
> superset package with a more lispy interface.
>
> One concern I have is that if we wrap a GSLL within a function, then
> we may end up passing variables by value from the top level down,
> which is inefficient.  I *hope* that if the second level wrappers are
> written as macros this dissapears.
>
> For example I defined the following macro:
> (defmacro solve-tridiag (d e f b)
>    `(letm ((d* (vector-double-float ,d))
>            (e* (vector-double-float ,e))
>            (f* (vector-double-float ,f))
>            (x* (vector-double-float (make-array (length ,d)
>                                                 :element-type 'double-float
>                                                 :initial-element 0d0)))
>            (b* (vector-double-float ,b)))
>       (solve-tridiagonal d* e* f* b* x*)
>       (data x*)))
>
> I am not too strong with macros, but I am hoping that since the macro
> is expanded at compile time, there is no passing by value of variables
> d,e,f,b.
>
>>
>> Zach
>>
>
> I hope the GSLL's author, Liam, takes these comments in stride, since
> he did awesome work, and what we are discussing here is the "dressing"
> on an otherwise a very cool package.
>
>
> Mirko
>
>>>
>>> I find the naming convention in gsll inconvenient.  For example the
>>> routine solve-tridiagonal is a wrapper for gsl_linalg_solve_tridiag.
>>> To use it to solve a system defined by vectors d e f b, one needs to
>>> use a letm block to this effect:
>>>
>>>  (letm ((d* (vector-double-float d))
>>>         (e* (vector-double-float e))
>>>         (f* (vector-double-float f))
>>>         (x* (vector-double-float (make-array (length d) :element-type
>>> 'double
>>>                                              :initial-element 0d0))
>>>         (b* (vector-double-float b)))
>>>    (solve-tridiagonal d* e* f* b* x*)
>>>    (data x*))
>>>
>>> Using the routine solve-tridiagonal is still not convenient, because
>>> one still needs to convert the argument vectors via the
>>> vector-double-float, obscuring the code.  If I have multiple calls, I
>>> will have to repeat these, or define my own interface function.  And
>>> here is the problem: *the very nice name solve-tridiagonal is taken*.
>>> I could name it solve-tridiag, but sooner or later, I will make a
>>> mistake and call the wrong function with the incorrect arguments.
>>>
>>> Ideally, once we have gsll, one would just need to do
>>> (solve-tridiagonal d e f b).  To accomplish that, gsll would need to
>>> use the following convention:
>>>  - the c-code wrapper would be named the same as the c-code, except
>>> with the underscores replaced with dashes.  Thus we would have
>>> (defmfun gsl-linalg-solve-tridiag (diag e f b x)
>>>  "gsl_linalg_solve_tridiag"
>>>  (((pointer diag) gsl-vector-c) ((pointer e) gsl-vector-c)
>>>   ((pointer f) gsl-vector-c) ((pointer b) gsl-vector-c)
>>>   ((pointer x) gsl-vector-c))
>>>  :invalidate (x)... etc)
>>>
>>>  - Users/contributors can define interface routines that would link to
>>> the gsll routine:
>>> (defun solve-tridiag (d e f b)
>>>  (letm ((d* (vector-double-float d))
>>>          (e* (vector-double-float e))
>>>          (f* (vector-double-float f))
>>>          (x* (vector-double-float (make-array (length d) :element-type
>>> 'double
>>>                                              :initial-element 0d0))
>>>          (b* (vector-double-float b)))
>>>     (solve-tridiagonal d* e* f* b* x*)
>>>     (data x*))
>>>
>>> (I have not tried it, but maybe macros should be better to remove the
>>> pass-by-value cost of calling the routine).
>>>
>>> So, what am I missing?
>>>
>>> Thanks,
>>>
>>> Mirko
>>> _______________________________________________
>>> Gsll-devel mailing list
>>> Gsll-devel at common-lisp.net
>>> http://common-lisp.net/cgi-bin/mailman/listinfo/gsll-devel
>>
>>
> _______________________________________________
> Gsll-devel mailing list
> Gsll-devel at common-lisp.net
> http://common-lisp.net/cgi-bin/mailman/listinfo/gsll-devel
>



More information about the gsll-devel mailing list