[Haskell-cafe] An interesting toy

Derek Elkins derek.a.elkins at gmail.com
Sat May 5 16:33:03 EDT 2007


Andrew Coppin wrote:
> Greetings.
> 
> I have something which you might find mildly interesting. (Please don't 
> attempt the following unless you have some serious CPU power available, 
> and several hundred MB of hard drive space free.)
> 
>   darcs get http://www.orphi.me.uk/darcs/Chaos
>   cd Chaos
>   ghc -O2 --make System1
>   ./System1
> 
> On my super-hyper-monster machine, the program takes an entire 15 
> minutes to run to completion. When it's done, you should have 500 images 
> sitting in front of you. (They're in PPM format - hence the several 
> hundred MB of disk space!) The images are the frames that make up an 
> animation; if you can find a way to "play" this animation, you'll be 
> treated to a truely psychedelic light show! (If not then you'll just 
> have to admire them one at a time. The first few dozen frames are quite 
> boring by the way...)
> 
> If you want to, you can change the image size. For example, "./System1 
> 800" will render at 800x800 pixels instead of the default 200x200. (Be 
> prepaired for /big/ slowdowns!)
> 
> *What is it?*
> 
> Well, it's a physical simulation of a "chaos pendulum". That is, a 
> magnetic pendulum suspended over a set of magnets. The pendulum would 
> just swing back and forth, but the magnets perturb its path in complex 
> and unpredictable ways.
> 
> However, rather than simulate just 1 pendulum, the program simulates 
> 40,000 of them, all at once! For each pixel, a pendulum is initialised 
> with a velocity of zero and an initial position corresponding to the 
> pixel coordinates. As the pendulums swing, each pixel is coloured 
> according to the proximity of the corresponding pendulum to the tree 
> magnets.
> 
> *Help requested...*
> 
> Can anybody tell me how to make the program go faster?
> 
> I already replaced all the lists with IOUArrays, which resulted in big, 
> big speedups (and a large decrease in memory usage). But I don't know 
> how to make it go any faster. I find it worrying that the process of 
> converting pendulum positions to colours appears to take significantly 
> longer than the much more complex task of performing the numerical 
> integration to discover the new pendulum positions. Indeed, using GHC's 
> profiling tools indicates that the most time is spent executing the 
> function "quant8". This function is defined as:
> 
>   quant8 :: Double -> Word8
>   quant8 = floor . (0xFF *)
> 
> I can't begin to /imagine/ how /this/ can be the most compute-intensive 
> part of the program when I've got all sorts of heavy metal maths going 
> on with the numerical integration and so forth...! Anyway, if anybody 
> can tell me how to make it run faster, I'd be most appriciative!
> 
> Also, is there an easy way to make the program use /both/ of the CPUs in 
> my PC? (Given that the program maps two functions over two big IOUArrays...)
> 
> Finally, if anybody has any random comments about the [lack of] qualify 
> in my source code, feel free...

Try adding strictness annotations to all the components of all your data 
structures (i.e. put a ! before the type).  Not all of the need it, but I doubt 
any need to be lazy either.  Probably the reason quant8 seems to be taking so 
much time is that it is where a lot of stuff finally gets forced.  Certainly, 
for things that are "primitive" like Colour and Vector you want the components 
to be strict, in general.

I did this for the program and ran System1 100 and it took maybe a couple of 
minutes, it seemed to be going at a decent clip.  200x200 should take 4 times 
longer, I assume, and I still don't see that taking 15 minutes. This is on a 
laptop running on a Mobile AMD Sempron 3500+.  Also, you have many many 
superfluous parentheses and use a different naming convention from 
representative Haskell code (namely camelCase).


More information about the Haskell-Cafe mailing list