Sign In
Forgot Password?
Sign In | | Create Account

Less puzzled

Some weeks ago, I made a posting in which I presented some code and then considered how it might be optimized and asked for input from readers. I was confident that I would not have found every possibility. Indeed, there were some useful comments, which I really appreciated. [It is nice to know that there is someone out there!]

Apart from the comments, I had an email from Michael Luber in Germany, who looked at the problem in some detail. With his permission, I have reproduced his results here …

I also like puzzles very much and, therefore, I would like to comment on this post.

I played around a bit and also found that much of what I could think of would probably addressed by most compilers.

However, in the end, I came up with this:

/*******************************************************************/
#define ITERATIONS 50
int mandelbrot(float a)
{
int i;
float b = a;
for (i=0; i<ITERATIONS; i++)
{
if (*((unsigned int*) &b) & (unsigned int)0x40000000)
{
return i;
}
b = b * b + a;
}
return i;
}
/*******************************************************************/

Here is what I considered:

  • Some compilers might initialize all uninitialized auto variables with zero, so I preferred to put a declaration of b with the assignment of a to it as a single statement. (As Peter already did).
  • I would rather let the variable i run from zero to (ITERATIONS – 1). This may save initializing it (see above), and saves the subtraction of 1 in the return statement.
  • This also allows i to be returned instead of ITERATIONS, if the for-loop runs to completion, which may save loading the constant ITERATIONS into a register (assuming i already is in a register).
  • For checking if the absolute value of a float is greater than 2, I just check for the second bit is set, which should work considering how floats are represented in memory. Of course, this “hack” introduces a hardware dependency, which is generally not a good idea. However, if the requirement is for performance above all, I could consider that. On x86-gcc, this trick reduces the check to a total of four instructions, including those for loading the float from stack as well as the conditional jump:
mov -0x8(%ebp),%eax
and $0x40000000,%eax
test %eax,%eax
je 0x4010bd

Maybe I would put this in a macro and add some compile-time checks to be safe, in case the compiler changes, or I go to 64-bit or something like that.

I’m also aware that my code checks for >=2 instead of >2, but when it comes to comparison of floating point numbers, this seems acceptable.

More Blog Posts

About Colin Walls Follow on Twitter

Colin WallsI have over twenty-five years experience in the electronics industry, largely dedicated to embedded software. A frequent presenter at conferences and seminars and author of numerous technical articles and two books on embedded software, I am a member of the marketing team of the Mentor Graphics Embedded Systems Division, and am based in the UK. Away from work, I have a wide range of interests including photography and trying to point my two daughters in the right direction in life. Learn more about Colin, including his go-to karaoke song and the best parts of being British: http://go.mentor.com/3_acv Visit The Colin Walls Blog

More Posts by Colin Walls

Comments

No one has commented yet on this post. Be the first to comment below.

Add Your Comment

Please complete the following information to comment or sign in.

(Your email will not be published)

Archives

 
Online Chat