Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Problems calling a variadic Java function from Clojure

I'm having a play with the Java NIO.2 API from JDK 7.

In particular, I want to call the method: Paths#get(String first, String... more)

This is a static method which takes in at least one string, and returns a Path object corresponding to it. There's an overloaded form: Paths#get(URI uri)

However, I can't seem to call the top method from Clojure. The nearest I can seem to get is this:

(Paths/get ^String dir-fq (object-array 0))

which fails with:

java.lang.ClassCastException: [Ljava.lang.Object; cannot be cast to [Ljava.lang.String;

as you might expect. After all, we're passing in an Object[] to something that's expecting String[].

I've tried removing the (object-array) form - but that just causes Clojure to try to call the get(URI) method - both with and without the type hint.

Passing nil as the second argument to Paths#get(String, String...) causes the right method to be called, but Java 7 then fails with an NPE.

I can't seem to find a way in Clojure to express the type String[] - I'm guessing I either need to do that or provide a hint to the dispatch system.

Any ideas?

like image 204
kittylyst Avatar asked Apr 12 '11 16:04

kittylyst


1 Answers

As you noticed, it doesn't want an Object[], it wants a String[]. object-array does exactly what it says: it makes an array of objects. If you want to create an array with some different type, make-array and into-array are your friends. For example here:

(Paths/get "foo" (into-array String ["bar" "baz"]))

The String specifier there is optional in this case: if you leave out the array's desired type, Clojure uses the type of the first object as the array's component type.

like image 69
amalloy Avatar answered Nov 15 '22 09:11

amalloy