Fork me on GitHub
#clojure-dev
<
2019-09-02
>
andy.fingerhut08:09:46

Is there a way to take a deftype and use its class in Java source code?

andy.fingerhut08:09:40

I know I could create Java source code for a similar class with the same attributes, fields, etc., but that would not be the same class, I don't think.

cgrand08:09:34

if the deftype is an AOT lib it should just work, if it’s in the same project the build will be unusual (and IDEs may be confused).

andy.fingerhut08:09:48

and the only reason I have for asking is to write as high performance Java as possible accessing instances of such a class, so reflection API is not a good contender for this purpose.

andy.fingerhut08:09:51

Hmmm. It might be an AOT lib, given that the deftype I have in mind is the Vec type in Clojure itself.

andy.fingerhut08:09:51

How would you compile a Java source file that accesses the class that is defined via the deftype? I was thinking that it would need a Java source version of the class definition, but are you saying that a .class file produced via AOT on Clojure code is enough?

andy.fingerhut08:09:19

I will go hack up a quick experimental Java source file with this to see if I can get it working. Thanks.

cgrand08:09:54

$ cat src/Main.java
class Main {
  public void main() {
    new clojure.core.Vec(); // pass proper args for compilation to succeed
  }
}
$ javac -cp ~/.m2/repository/org/clojure//clojure/1.10.0/clojure-1.10.0.jar src/Main.java
src/Main.java:3: error: constructor Vec in class Vec cannot be applied to given types;
    new clojure.core.Vec();
    ^
  required: Object,int,int,Object,Object,Object
  found: no arguments
  reason: actual and formal argument lists differ in length
1 error

andy.fingerhut08:09:57

Thanks. I was distracted by something else for a while, and my experiment had not started yet. Looks good.

andy.fingerhut17:09:42

yep, I can get a full call working that way. Thanks.

cfleming23:09:27

@andy.fingerhut I do this in Cursive. One thing to be aware of is that loading the class will not by default load its containing namespace, so if you call other functions from that namespace they will fail unless you use the :load-ns true option to deftype.