LogicChains
LogicChains

Reputation: 4412

Why is the same OpenGL function performing so differently in Clojure than in Java?

For fun I'm doing a simple OpenGL benchmark of various languages, and I just completed a Clojure implementation. It was running quite slow, however, so I decided to profile it with VisualVM, and I obtained some rather odd results. The following are snapshots from profiles of the Java and Clojure version respectively (both have identical rendering logic)

Java profiling screencap

Clojure profiling screencap

Note that glPopMatrix is the function taking up the most time in the Clojure implementation, by a significant margin, yet in the Java implementation glDrawArrays takes far more time. The code for the Clojure version is:

(defn render-pt [apt]
  (GL11/glPopMatrix)
  (GL11/glPushMatrix)
  (GL11/glTranslatef (:x apt) (:y apt) (- 0 (:z apt)) )
  (GL11/glScalef (* (:R apt) 2) (* (:R apt) 2) (* (:R apt) 2) )
  (GL11/glDrawArrays GL11/GL_QUADS 0 24)
  apt)

The function render-pt is mapped to an array of pt.

The code for the Java version is:

for (int i = minPt; i < numPts; i++) {
    Pt pt = Pts[i];
    GL11.glPopMatrix();
    GL11.glPushMatrix();
    GL11.glTranslatef(pt.X, pt.Y, -pt.Z);
    GL11.glScalef(pt.R * 2, pt.R * 2, pt.R * 2);
    GL11.glDrawArrays(GL11.GL_QUADS, 0, 24);
}

The two functions seem the same to me; is there some mistake I'm making? Or am I reading the profile wrong?

Upvotes: 2

Views: 213

Answers (1)

noisesmith
noisesmith

Reputation: 20194

Some differences between those functions:

(:x apt) always returns a boxed numeric value, since it is not type hinted. pt.X can likely return an unboxed numeric primitive, depending on the definition of Pt.

(:x apt) will do a hash lookup rather than the faster slot lookup that pt.X does (unless apt is a Clojure record, you don't show enough code for me to know which this is so I assume it is a hash-map).

Numeric literals are Long by default in Clojure, Integer by default in Java.

Upvotes: 2

Related Questions