[Haskell-cafe] Code review: efficiency question

ajb at spamcop.net ajb at spamcop.net
Mon May 1 19:44:44 EDT 2006


G'day all.

Quoting Brian Hulley <brianh at metamilk.com>:

> Hi -
> I started off writing the following piece of monadic code:
>
>     let
>           drawModal :: Control -> ManagerM ()
>           drawModal c = do -- details omitted
>
>           -- Prolog style coding...
>           drawModals :: [Control] -> ManagerM ()
>           drawModals [] = return ()
>           drawModals (c:cs) = do
>                                                drawModals cs
>                                                drawModal c
>     drawModals cs
>
> then it struck me that I should have not bothered with drawModals and
> instead should just have used:
>
>     mapM_ drawModal (reverse cs)
>
> However, while this looks more elegant, it is less efficient?

I suspect it depends how long the list is.  The original drawModals
would probably be more efficient for small lists, because it doesn't
require creating an intermediate list.  OTOH, it may well be less
efficient for longer lists because it can't take advantage of tail
recursion.

> I'm trying to get a rough idea so I can decide whether to write helper
> functions such as drawModals in future or whether I should always just use
> the most elegant code instead.

This is a question that is independent of Haskell.  You should ALWAYS
write the most elegant code first, and only make it uglier if it's not
fast enough.

(Note: Some programs are non-Knuthian in that they do require attention
to efficiency before writing any code.  But even then, it's usually
worth putting effort into designing a good API first.  That way, you
can write the elegant code first, and if/when you have to replace it
later, the good API insulates the rest of the code from the change.)

Cheers,
Andrew Bromage


More information about the Haskell-Cafe mailing list