[Haskell-cafe] Type System vs Test Driven Development

Serge Le Huitouze serge.lehuitouze at gmail.com
Wed Jan 12 12:16:26 CET 2011

Evan Laforge <qdunkan at gmail.com> wrote:

> QuickCheck seems to fit well when you have small input and output
> spaces, but complicated stuff in the middle, but still simple
> relations between the input and output.  I think that's why data
> structures are so easy to QuickCheck.  I suppose I should look around
> for more use of QuickCheck for non-data structures... the examples
> I've seen have been trivial stuff like 'reverse . reverse = id'.

I second this feeling...

For example, I've never seen (I've not looked hard, though) Quickcheck's
testing applied on graphs. Generating "interesting" (whatever that means
for your particular problem) graphs doesn't seem to be a trivial test, even
if it's a mere data structure...
Does anyone know of such examples?

Maybe genetic programming producing graphs is of relevance here (where
generating candidate graphs have exactly the same problem).

Also, I wonder how you guys do when you're trying to tests code
using a lot of  numbers (be them floating point or even integer).

E.g., integers:
A code doing addition and substraction of some sort.
A property such as "X = (X add Y) sub Y" is easily falsifiable when
the number of bits of your integer is too small for your numbers.

E.g. floating point numbers:
A code doing coordinate transformations of some sort.
Properties akin to "roundtripping" can be easily formulated (e.g.
"X = trfY_toX(trfX_toY(X))"), but they'll be falsified often due to lost
bits in the mantissa.
Replacing strict equality (almost always meaningless for floats) with
approximate equality will work.
However, definitions of such an approximate equality might vary (the
immediate idea is to compare the difference of the two numbers with
a small "epsilon", say 10^-9, but that will obviously not work if you
numbers are around 10^-12...).

And there are also, of course, overflows and underflows, and singularities (e.g.
division by zero), non invertibility...

So, in addition to defining the approximation (not always easy as I tried
to "demonstrate" above) to be used in comparisons, one probably needs
ad'hoc generators whose complexity might very well exceed that of
the code one wants to test...

So, do you have any "methodology" for such use cases?


More information about the Haskell-Cafe mailing list