Fully transitive const is not necessary

Walter Bright newshound1 at digitalmars.com
Wed Apr 2 18:40:00 PDT 2008


Bill Baxter wrote:
> So does that mean
> 
>   pure int f(const Class c)
>   { ...
>   }
> 
> will *not* be allowed?  Because some part of c *could* change, even if 
> it's not f() doing the changing.  I.e. another thread could be changing 
> c concurrently.

Right. That declaration of f is erroneous.

> If so, that seems unnecessarily restrictive to me.  Any side effect or 
> indeterminacy of f() in that case is not because of f()'s doing.  So 
> f()'s behavior *is* pure even if it takes a const argument.  It's not 
> f's fault if the environment it's living in is unstable.

A function is pure or it isn't, there really isn't any room for 
"unstable" purity, or the point of purity is lost.

Look at it another way. You can take the value of the bits pushed on the 
stack as arguments to a pure function, and compare that with previous 
bits passed to the same function, and if there's a binary bit match, you 
can skip calling the function and return a previously cached result.

If that cannot be done, then the function is NOT pure.

> Maybe there need to be two levels of pure?  One says this function by 
> itself has no side effects, the other says additionally that the 
> function is invariant with respect to the environment.  The former 
> category of functions can all be run in parallel safely provided there 
> are no other threads modifying the environment simultaneously.

No, you cannot run them simultaneously. The problem with const (instead 
of invariant) is that the transitive state of the passed object is NOT 
guaranteed to be the same:

pure int foo(const C c) { return c.p[0]; }
class C { int* p; }
C c;
c.p = q;
int i = foo(c);
q[0] = 3;
int j = foo(c);

Note that these foo's cannot be run in parallel, despite c never having 
been changed. I think that notion of purity is not useful.



More information about the Digitalmars-d mailing list