Git Product home page Git Product logo

jise's People

Contributors

athos avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Forkers

crhough eoliphan

jise's Issues

Array set example?

Hello, this is a really nice library. There's a discussion over on zulip over porting a java implementation of a method that generates random strings, where most of the path is going through char arrays. We seem to be paying an unavoidable cost in uncheckedIntCast when doing any array access with literals (since the literal numbers are always longs), where javac gets away with this. I have a repo here with the corresponding java implementation and my current attempt at porting it to JiSE, cited below. I was using both aset and aget, per some of the examples, and it looks like we're as fast as the clojure example if unchecked-math is enabled (which will emit uncheckedIntCast s for us). That still tends to be about 8% slower on my machine, worse on others (if you believe in the ns accuracy of criterium). Is there a way to ensure that the indices for aset are actually being represented as ints in the resulting class definition (such as a different array set syntax, I was unable to figure out..)? Or is the expected path to use aset/aget as I have done? I found that the direct array access is possible in the benchmark example you provided. Thanks for any insight!

^:public
(defclass Rand
  (def ^:public ^:static ^chars tbl
    (new [char] [\- \0 \1 \2 \3 \4 \5 \6 \7 \8
                 \9 \A \B \C \D \E \F \G \H \I
                 \J \K \L \M \N \O \P \Q \R \S
                 \T \U \V \W \X \Y \Z \_ \a \b
                 \c \d \e \f \g \h \i \j \k \l
                 \m \n \o \p \q \r \s \t \u \v
                 \w \x \y \z]))
  ^:public ^:static  ^String
  (defm genId []
    (let [^ThreadLocalRandom tlr (ThreadLocalRandom/current)
          ^long  l1 (.nextLong tlr)
          ^long  l2 (.nextLong tlr)
          ^chars rt (new [char] 22)]
      (aset rt 21 (tbl ^int (&  l1 0x3f)))
      (aset rt 20 (tbl ^int (&  (>>> l1 6) 0x3f)))
      (aset rt 19 (tbl ^int (&  (>>> l1 12) 0x3f)))
      (aset rt 18 (tbl ^int (&  (>>> l1 18) 0x3f)))
      (aset rt 17 (tbl ^int (&  (>>> l1 24) 0x3f)))
      (aset rt 16 (tbl ^int (&  (>>> l1 30) 0x3f)))
      (aset rt 15 (tbl ^int (&  (>>> l1 36) 0x3f)))
      (aset rt 14 (tbl ^int (&  (>>> l1 42) 0x3f)))
      (aset rt 13 (tbl ^int (&  (>>> l1 48) 0x3f)))
      (aset rt 12 (tbl ^int (&  (>>> l1 54) 0x3f)))
      (aset rt 11 (tbl ^int (&  (>>> l1 60) 0x3f)))
      (aset rt 10 (tbl ^int (&  l2 0x3f)))
      (aset rt 9  (tbl ^int (&  (>>> l2 6) 0x3f)))
      (aset rt 8  (tbl ^int (&  (>>> l2 12) 0x3f)))
      (aset rt 7  (tbl ^int (&  (>>> l2 18) 0x3f)))
      (aset rt 6  (tbl ^int (&  (>>> l2 24) 0x3f)))
      (aset rt 5  (tbl ^int (&  (>>> l2 30) 0x3f)))
      (aset rt 4  (tbl ^int (&  (>>> l2 36) 0x3f)))
      (aset rt 3  (tbl ^int (&  (>>> l2 42) 0x3f)))
      (aset rt 2  (tbl ^int (&  (>>> l2 48) 0x3f)))
      (aset rt 1  (tbl ^int (&  (>>> l2 54) 0x3f)))
      (aset rt 0  (tbl ^int (&  (>>> l2 60) 0x3f)))
      (String. rt))))

Allow different types for the second and third operands of conditional operator

According to JLS 15.25, typing the conditional operator never fails unless it includes an invocation of a void method. However, the current implementation throws VerifyError when the second and third operands differs in type:

user=> (defclass C ^String (defm m [^int x] (str (if (== x 0) "foo" 1))))
Syntax error (VerifyError) compiling at (REPL:1:1).
Bad type on operand stack
Exception Details:
  Location:
    user/C.m(I)Ljava/lang/String; @17: invokevirtual
  Reason:
    Type top (current frame, stack[1]) is not assignable to 'java/lang/String'
  Current Frame:
    bci: @17
    flags: { }
    locals: { 'user/C', integer }
    stack: { 'java/lang/StringBuilder', top }
  Bytecode:
    0000000: bb00 0e59 b700 0f1b 9a00 0812 11a7 0004
    0000010: 04b6 0015 b600 19b0                    
  Stackmap Table:
    same_locals_1_stack_item_frame(@16,Object[#14])
    full_frame(@17,{Object[#2],Integer},{Object[#14],Top})

user=> 

would lambdas be supported?

It'd be great to have direct lambda support instead of using the clojure.lang.IFn interface.

Is that on the roadmap and how difficult would it be to get working?

Why is it so un-java?

Why does it use def, square brackets, and other vestigal clojure syntax? I can't give this to my Java friends, they'd laugh. There is a JiSE out there waiting to be discovered that they wouldn't laugh it.

Are there any comparison benchmarks for the examples?

I'm really curious about the typical speeds for the algorithms you implemented (like AOBench).

I ran it, it feels really fast but I'm not sure what a comparison might be.

Do you have any comparisons that you might have ran yourself?

Unexpected use of final in emitted class

Original java:

ThreadLocalRandom tlr = ThreadLocalRandom.current();
long l1 = tlr.nextLong(), l2 = tlr.nextLong();
char[] rt = new char[22];
 rt[21] = tbl[(int)l1 & 0x3f]; l1 = l1 >>> 6;
 rt[20] = tbl[(int)l1 & 0x3f]; l1 = l1 >>> 6;
 rt[19] = tbl[(int)l1 & 0x3f]; l1 = l1 >>> 6;

Corresponding JiSE:

(let [^ThreadLocalRandom tlr (ThreadLocalRandom/current)
      ^long  l1 (.nextLong tlr)
      ^long  l2 (.nextLong tlr)
      ^chars rt (new [char] 22)]
(aset rt 21 (tbl ^int (&  l1 0x3f)))(set! l1 (>>> l1 6))
(aset rt 20 (tbl ^int (&  l1 0x3f)))(set! l1 (>>> l1 6))
(aset rt 19 (tbl ^int (&  l1 0x3f)))(set! l1 (>>> l1 6))
...
)

Inspected with clj-decompiler, using (decompile ...), gives:

final char[] array = new char[22];
final ThreadLocalRandom current = ThreadLocalRandom.current();
final long nextLong = current.nextLong();
final long nextLong2 = current.nextLong();
array[21] = RandM.tbl[(int)(nextLong & 0x3FL)];
final long n = nextLong >>> 6;
array[20] = RandM.tbl[(int)(n & 0x3FL)];
final long n2 = n >>> 6;
array[19] = RandM.tbl[(int)(n2 & 0x3FL)];
...

long variable in let is set to final. Is there a way to allow it to mutate?

Annotations?

Curious how much additional effort would be required for annotations. I am helping work through porting an example from optaplanner which is "heavily" class-based and requires lots of annotations to communicate with the framework. Most of clojure's deftype (with annotation support) worked here, however we end up with problems since the field types are "always" Object, regardless of typehint. So optaplanner will complain that the field does not return a constrained type (List or array). Looking at custom bytecode generation with insn, but I figured I would see if JiSE could be closer...

Cannot find methods defined in Object class for interface types

user=> (require '[jise.utils :as jise])
nil
user=> (jise/do (let [^java.io.Serializable s "foo"] (.toString s)))
Syntax error macroexpanding jise.core/class at (form-init7183457418990174559.clj:64:4).
Error: cannot find symbol
  symbol: method toString(no arguments)
  location: class java.io.Serializable (/private/var/folders/mr/bf82sldd78g9822yxqgzd12h0000gn/T/form-init7183457418990174559.clj:1:47)
user=>

Whereas:

user=> (jise/do (let [^String s "foo"] (.toString s)))
"foo"
user=>

This is essentially due to the fact that the current implementation of t/get-methods does not consider the Object class as a supertype of any interface type:

user=> (t/get-methods nil nil (t/tag->type 'java.io.Serializable) "toString")
nil
user=> (t/get-methods nil nil (t/tag->type 'String) "toString")
({:class #object[clojure.asm.Type 0x3d7eb9c1 "Ljava/lang/String;"],
  :interface? false,
  :param-types [],
  :return-type #object[clojure.asm.Type 0xbc97527 "Ljava/lang/String;"],
  :access #{:public}})
user=>

Getting Example to Work

@athos: I'm looking to get jnr-ffi working with jise and am porting the Gettimeofday example here:

https://github.com/jnr/jnr-ffi-examples/blob/master/gettimeofday/src/main/java/gettimeofday/Gettimeofday.java

I'm having problems compiling the defclass form. Would you please take a look and let me know what I'm doing wrong.

https://gist.github.com/zcaudate/f05001f6cc38a8a02f9b0892bab02a82

I'm getting this error here, which I'm not sure is defclass or jnr related.

 Error: constructor jnr.ffi.Struct$time_t in class
   jnr.ffi.Struct$time_t cannot be applied to given types
   (/Users/chris/Development/caudata/statstrade/statstrade-server/src/statstrade/lib/curl.clj:55:26)
   {:column 26,
    :line 55,
    :alternatives
    ({:param-types
      [#object[clojure.asm.Type 0x29c9e0cb "Ljnr/ffi/Struct;"]],
      :access #{:public}}
     {:param-types
      [#object[clojure.asm.Type 0x23d3c400 "Ljnr/ffi/Struct;"]
       #object[clojure.asm.Type 0x7093025d "Ljnr/ffi/Struct$Offset;"]],
      :access #{:public}})}

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    ๐Ÿ–– Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. ๐Ÿ“Š๐Ÿ“ˆ๐ŸŽ‰

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google โค๏ธ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.