Saturday, September 19, 2009

A Good Mix 22: Win a book, Mandlebrot Performance, Double clicking in Silverlight and more...

Another collection of blog entries and articles related to IronPython and the Dynamic Language Runtime.
Allan Juhl Petersen has a competition running until 29th September where you can win a book on IronPython (and a good book it is too) or F#:
I have created 7 questions, in different programming languages such as C#, F#, Ironpython, C++, Java and of course the well known and liked true or false. The questions are designed to give a number of points, where the maximum number of points given can be read in the text of the assignment. The rules are simple, the one with the highest score on points, will win. Points will be given for correctness and effort. An assignment might give 6 point, but if not entirely correct, it will be given some points for effort.
The winner gets Office 2007 Student version and gets to choose between two books ? Foundations of F# or IronPython in Action - and the runner-up gets the one that the winner did not choose.
This article will compare the latest incarnations of Ruby, with the latest in Python, Groovy, PHP, Lua, Perl and Java too, to have a comparison with a pre-compiled language. We will see, how scripting languages behave if applied to fractal geometry, more precisely an family Mandelbrot algorithm.

Browsing on the net, I found a comparison very interesting but a bit dated, dates back more than two years ago. Since then things have changed and I took advantage to make an update, not including all of those languages but only for more known. This is an opportunity to compare Ruby and Python versions even in their Java and. NET, an intention that I had since long time.

These are the performance results obtained from an average of five runs, took after have executed some void attempts (I have not trusted the VM startup):

Language      Time (in seconds)  slower than java
Java 6 update 15    0,153
Lua 5.1.4           0,815              5x
Php 5.3.0           2,083              14x
Python 2.6.2        2,269               15x
Python 3.1.1        1,566               10x
Jython 2.5.0        2,850               19x
Jruby 1.3.1         2,466               16x
Groovy 1.6.3        6,491               42x
Ruby 1.9.1 p129        2,688            18x
Ruby 1.8.6 p368        6,863            45x
Ruby 1.8.6 p111        9,709            63x
IronRuby 0.9.0        6,038             39x
IronPython 2.0.2     0,978              6x
Perl 5.10.0         2,722               18x

As you can see, for this type of calculation IronPython comes out faster than Ruby, IronRuby and CPython.
I have recently been wondering about how to build a generic system for parsing and processing lots of EDI messages in such a way that a minimum of work is needed when a new message type is to be processed by the system. The syntactic format of EDI messages is fairly consistent, but the semantics of particular fields are open for interpretation. Thus, I thought it should be possibly to write a general parser for turning a message into a tree structure (much like an abstract syntax tree for “the EDI language”) which would be appropriate as input to the processing phase of the system.

Having recently picked up “IronPython in Action” I decided to apply IronPython to the task. Since this was only an experiment, I decided to somewhat give up the idea of a tree structure and instead leverage the dynamic programming capabilities of IronPython. Given an EDI message at runtime I wanted to generate an object with properties corresponding to the segments, subsegments and elements of the message.
A new release for this mysterious project on the Japanese sourceforge site. The main project page has more details - but in Japanese.
Silverlight has a left click event for controls, but not a double click event. This makes for fun when implementing some user interfaces. The Evil Monkey Labs blog has an example of how to work around this in IronPython:
Silverlight rather oddly lacks a double click event. You can detect single click, but for double clicking you're on your own. I found some examples for C#, but none for IronPython and had, a few months ago, ported some code I found for IronPython.

I've been using it in application development and user testing for about 6 months and it works fairly well in both Silverlight 2 and 3, although YMMV.


  1. As far as fractal calculations go, I'm delighted to note that CPython+numpy is comfortably faster than Java.

  2. @bryancole where is the data for that? It isn't in the article I linked to.

  3. Plus IronPython with Numpy (via Ironclad) may or may not be faster still. :-)

  4. No, I added it as a comment.

    Here's my latest version:

    class Bench3(object):
    ....def __init__(self):
    ........print ('Rendering...')
    ........lower = -39/40.0
    ........upper = 38/40.0
    ........steps = 78j
    ........y,x = numpy.ogrid[lower:upper:steps, lower:upper:steps]
    ........i = self.start(x,y)
    ........out = numpy.empty(i.shape, dtype=numpy.byte)
    ........out[i==0] = 42
    ........for row in out:
    ....def start(self, x, y):
    ........"""x & y are now arrays of shape (nx, ny)
    ........c = (y - 0.5) + 1.j*x
    ........c_ = c.ravel()
    ........z = numpy.zeros(c_.shape, dtype=numpy.complex128)
    ........idx = numpy.arange(z.size)
    ........out = numpy.zeros(c.shape,
    ........out_ = out.ravel()
    ........logical_not = numpy.logical_not
    ........for i in xrange(1,MAX_ITERATIONS+2):
    ............z **= 2
    ............z += c_
    ............mask = (z.real + z.imag) <= BAILOUT
    ............idx_ = idx[logical_not(mask)]
    ............out_[idx_] = i
    ............z = z[mask]
    ............c_ = c_[mask]
    ........return out

    If you allow the .start() method to simply return a boolean array, it can go a bit faster (but the Pedants may complain).

    I'd be interested to hear how numpy performs through ironclad.


  5. Hmmm... I can't see my comment on the original blog posting either. Maybe it got anti-spammed. oh well.

  6. Boo hoo. Testing on another system shows only a 10-fold improvement between my numpy-version and vanilla python. This means java remains faster (and compiling the java version confirms this).

    Here's my times:

    python (original): 8.33s
    python (original+psyco): 1.0s
    python+numpy: 0.790s
    java-1.6: 0.42s
    Cython: 0.174s

    Now I should get on with some real work...


Note: only a member of this blog may post a comment.