type declaration best practices?
Per Bothner
per@bothner.com
Thu Nov 12 23:58:00 GMT 2009
On 11/12/2009 03:11 PM, Jamison Hope wrote:
> Is there a definitive set of best practices for declaring types of
> variables? I see mention here and there that using angle brackets is
> out, but they're still all over the place in Kawa sources and the Kawa
> homepage.
Angle brackets are semi-deprecated. I'm gradually fixing things
to remove angle-brackets - though I want to leave at least some, for
the sake of testing!
Similarly, there are still lots of older invoke and even the really
old primitive-virtual-method that should be replaced by colon-notation.
(invoke-static is still needed for some things.)
> These appear to all be valid and equivalent:
>
> (define (tagged-vector3f tag :: <symbol> x :: <float> y :: <float> z ::
> <float>) :: <pair>
> (cons tag (make <javax.vecmath.Vector3f> x y z)))
>
> (define (tagged-vector3f tag :: symbol x :: float y :: float z :: float)
> :: pair
> (cons tag (make javax.vecmath.Vector3f x y z)))
I didn't realize this worked - it's not my preferred style, as it seems
non-obvious how things are grouped. However, it is consistent with
how things work in define and let - i.e. you can just add an optional
:: TYPE. See below.
> (define (tagged-vector3f (tag symbol) (x :: float) (y :: float) (z ::
> float)) :: pair
> (cons tag (make javax.vecmath.Vector3f x y z)))
>
> (define (tagged-vector3f (tag symbol) (x float) (y float) (z float)) ::
> pair
> (cons tag (make javax.vecmath.Vector3f x y z)))
Likewise not my preferred style - I think including the colons helps.
But this is something I've been pondering, and perhaps a question
for the list. In define and let you can just add the optional :: TYPE
without having to add extra parentheses. I'm thinking a slight change,
in removing a space, might make things more readable:
(define (tagged-vector3f tag ::symbol x ::float y ::float z ::float)
::pair
(cons tag (make javax.vecmath.Vector3f x y z)))
(define xxx ::integer 123)
Or perhaps allow leaving out the preceding space as well:
(define (tagged-vector3f tag::symbol x::float y::float z::float)
::pair
(cons tag (make javax.vecmath.Vector3f x y z)))
(define xxx::integer 123)
I think PLT allows something like that, except using a single colon
- but that would conflict with colon notation, alas.
Implementation becomes a little tricky: The easiest mechanism
is to just define that there is a "delimiter" before and after
double-colon - that would just be a reader change (which would
be disabled in strict-R6RS-mode, if/when we provide that).
Comments?
> Likewise:
> (define-alias Vector3f <javax.vecmath.Vector3f>)
> (define-alias Vector3f javax.vecmath.Vector3f)
I recommend the latter these days.
> [or s/alias/namespace/g in that]
>
> Which of these are the preferred forms? Are there situations in which
> angle brackets are still required?
There might be, but I believe only in forms which are deprecated anyway.
> Also, I realize that there are differences between an alias and a
> namespace:
> (let ((x 3)) (define-namespace y x) (define-alias z x) (set! x 4) (list
> x y z))
> => (4 3 4)
> but it seems like when used with a class name as the second operand,
> both define-namespace and define-alias are chiefly useful in order to
> avoid having to repeatedly type a FQCN, like a Java import. So, which is
> truly conceptually closer to a Java import statement?
define-alias is generally preferable, though the documentation
isn't very helpful. I need to update this.
http://sources.redhat.com/ml/kawa/2008-q1/msg00074.html
> Which produces better code?
It should be the same.
> When declaring a variable's type, or as the first argument
> to the make procedure,
Btw - you know you can leave out the 'make' and use a
class as a "constructor function":
(java.lang.Integer "12")
or:
(java.lang.String[] "ab" "cd")
> is there a performance difference when using (1)
> a built-in type (an instance of gnu.bytecode.Type), (2) a
> fully-qualified class name, (3) a namespace, or (4) an alias?
Nope, as long as the name/namespace/alias are all known
at compile-time. If the lookup needs to be done at
run-time and we need to use reflection - then I don't know.
--
--Per Bothner
per@bothner.com http://per.bothner.com/
More information about the Kawa
mailing list