Communicating between in and out contracts
Andrei Alexandrescu
SeeWebsiteForEmail at erdani.org
Fri Oct 16 14:07:35 PDT 2009
Rainer Deyke wrote:
> Andrei Alexandrescu wrote:
>> class A {
>> int fun() { ... }
>> int gun(int) { ... }
>>
>> int foo()
>> in {
>> }
>> out(result) {
>> if (old.fun())
>> assert(old.gun(5));
>> else
>> assert(old.fun() + old.gun(6));
>> foreach (i; 1 .. old.fun())
>> assert(gun(i * i));
>> }
>> ...
>> }
>>
>> Now please tell what's cached and in what order.
>
> The following are cached, in this order:
> fun()
> gun(5)
> gun(6)
> Old values are calculated in the order in which they appear in the
> function, but only once each.
Rats, I meant assert(old.gun(i * i)). That's what compounds the
difficulty of the example.
> However, I strongly prefer the following syntax:
>
> class A {
> int fun() { ... }
> int gun(int) { ... }
>
> int foo()
> in {
> }
> out(result) {
> if (old(fun()))
> assert(old(gun(5)));
> else
> assert(old(fun()) + old(gun(6)));
> foreach (i; 1 .. old(fun()))
> assert(gun(i * i));
> }
> ...
> }
>
> This lets you distinguish between the following cases:
> old(f().g())
> old(f()).g()
>
> It also lets you cache non-members:
> old(arg);
> old(global_var);
>
> For example:
>
> void increment_global_counter() out {
> global_counter = old(global_counter) + 1;
> }
I honestly believe the whole "old" thing can't be made to work. Shall we
move on to other possibilities instead of expending every effort on
making this bear dance?
Andrei
More information about the Digitalmars-d
mailing list