Examples Wanted: Usages of "body" as a Symbol Name

Jonathan M Davis via Digitalmars-d digitalmars-d at puremagic.com
Fri Oct 7 04:43:03 PDT 2016


On Friday, October 07, 2016 10:57:00 Nick Treleaven via Digitalmars-d wrote:
> On Wednesday, 5 October 2016 at 19:45:20 UTC, Basile B. wrote:
> > In this case let's drop completely the contracts...you can put
> > them in the body, at the beg or at the end...
>
> Language support for contracts enables a super class to enforce
> contracts on its virtual methods.

It also allows the contracts to be effectively &&ed or ||ed when it comes to
the in and out contracts on virtual functions (IIRC, in contracts are ||ed
and out contracts are &&ed, but I can never remember and have to think it
through every time it comes up).

In any case, having explicit in and out contracts make it possible to make
them work correctly in the face of inheritance. And _in theory_ some aspects
of in contracts could be checked at compile time, which would make them
better than simply putting the assertions in the function body (though no
such compile time checking is currently implemented). Also, _in theory_, it
makes it possible to have the in and out contracts be compiled in or not
based on how the caller is compiled rather than the function being called
(which is really how it should work but unfortunately doesn't at present).

In practice, as it stands, aside from inheritance, I think that explicit in
and out contracts are pointless, because the in contracts can just be done
in the function body, and out contracts normally need to be handled by the
unit tests instead of an explicit out contract anyway (since in most cases,
what needs to be asserted about the result depends on knowing exactly what
the input was and knowing what the correct result for that input is, whereas
an out contract can only check for things that are true of all results). So,
I pretty much never use in our out contracts.

But the inheritance case is why they're still worth having in the language
even if they're mostly useless in practice.

What is theoretically more useful IMHO is invariants, but since they get
called before opAssign, it doesn't work to have an invariante for a type
that would ever be initialized with void or used with emplace. So, in
practice, I think that invariants are useless too, unfortunately. And my
past attempts to argue that the invariant shouldn't be called before
opAssign failed. So, I never use invariants anymore either. :(

- Jonathan M Davis



More information about the Digitalmars-d mailing list