John M. Dlugosz wrote: > PRE/POST on methods: > > " > When applied to a method, the semantics provide support for the "Design by > Contract" style of OO programming: a precondition of a particular method is > met if all the PRE blocks associated with that method return true. Otherwise, > the precondition is met if all of the parent classes' preconditions are met > (which may include the preconditions of their parent classes if they fail, > and so on recursively.) > > In contrast, a method's postcondition is met if all the method's POST blocks > return true and all its parents' postconditions are also met recursively. > " > > If the PRE blocks on the method don't all return true, it appeals to the > preconditions on the base class of the class defining the method? I don't > get it. Why would a class-level precondition override a method-level > precondition? Why bother defining them on the method, if they are ignored if > they are false anyway?
Finally one that I'm able to answer ;-)
class MyMath {
method sqrt($x:) {
PRE { $x >= 0 }
# your calculation here.
}
}
Now whenever you have an object of Type MyMath, you can be sure that
it's valid to pass any non-negative number to sqrt.
If a inherited class could harden that precondition, that assumption
would be false. That's why it's only allowed to weaken preconditions:
class MyComplexMath is MyMath {
method sqrt($x:){
PRE { True }
# your calculation here
}
}
This is described in depth in "Object oriented software construction" by
Bertrand Meyer.
If you want to harden a precondition, you can revert to addtional methods:
class MyMath {
method can_take_sqrt($x:){
$x >= 0;
}
method sqrt($x:){
PRE { $x.can_take_sqrt }
...
}
}
class MyComplexMath is MyMath {
method can_take_sqrt($x:){
True
}
...
}
That way a user of class MyMath can always call can_take_sqrt() to check
if she can satisfy the precondition.
Cheers,
Moritz
--
Moritz Lenz
http://moritz.faui2k3.org/ | http://perl-6.de/
signature.asc
Description: OpenPGP digital signature
