
Am 20.02.2017 um 23:05 schrieb Richard A. O'Keefe
: On 15/02/17 10:35 AM, Olaf Klinke wrote:
You should not have to write tests for functions you did not define.
Correct me if I'm wrong, but any property of max can be derived from the properties of <=.
Unfortunately, this isn't quite true.
Suppose we have two values x y such that x <= y && y <= x && x == y *BUT* x and y are distinguishable some other way. For example, suppose we are modelling rational numbers by pairs (n,d) *without* insisting that gcd(n,d) == 0. Then we have (n1,d1) == (n2,d2) = n1*d2 == n2*d1 compare (n1,d1) (n2,d2) = compare (n1*d2) (n2*d1) BUT (1,2) and (2,4), while ==, are none-the-less distinguishable.
Now ask about max x y. If we have
max a b = if a > b then a else b
then max x y delivers y. But if we have
max a b = if a < b then b else a
then max x y delivers x, and these two results can be distinguished.
If you define an Ord instance that is only a preorder rather than a total order, and then downstream rely on functions f that violate the property x == y implies f x == f y, I'd call that poor design. The above formula would be something for a Quickcheck module. That said, I myself found it handy in the past to define such preordered types.
I know and freely admit that if I want a version of max that satisfies stronger conditions than Ord can guarantee, it is up to me to write it. Or rather, be aware of the standard implementation of max in Data.Ord. Anyways, you are right: Since the type system can not guarantee that every Ord instance is actually a total order, test coverage statistics won't help us here.
Regards, Olaf