www.digitalmars.com         C & C++   DMDScript  

digitalmars.D - More on purity

reply bearophile <bearophileHUGS lycos.com> writes:
This was discussed a little in D.learn. Is code like this going to compile in
some future DMD versions, like DMD 2.058? I hit situations like this often in
my code:



int[] foo1(immutable int[] a) pure {
    return new int[a.length];
}

int[] foo2(in int[] a) pure {
    return new int[a.length];
}

void main() {
    immutable int[] arr1 = [1, 2, 3];
    immutable int[] r1 = foo1(arr1); // OK

    const int[] arr2 = [1, 2, 3];
    immutable int[] r2 = foo2(arr2); // error
}


Currently it gives:
Error: cannot implicitly convert expression (foo2(arr2)) of type int[] to
immutable(int[])


If code like that can't be accepted in future D/DMD versions, then I think DMD
should give an error message that explains why the r2 implicitly conversion is
not acceptable (while the implicitly conversion to r1  is acceptable).

Bye,
bearophile
Dec 21 2011
parent reply Timon Gehr <timon.gehr gmx.ch> writes:
On 12/21/2011 08:53 PM, bearophile wrote:
 This was discussed a little in D.learn. Is code like this going to compile in
some future DMD versions, like DMD 2.058? I hit situations like this often in
my code:



 int[] foo1(immutable int[] a) pure {
      return new int[a.length];
 }

 int[] foo2(in int[] a) pure {
      return new int[a.length];
 }

 void main() {
      immutable int[] arr1 = [1, 2, 3];
      immutable int[] r1 = foo1(arr1); // OK

      const int[] arr2 = [1, 2, 3];
      immutable int[] r2 = foo2(arr2); // error
 }


 Currently it gives:
 Error: cannot implicitly convert expression (foo2(arr2)) of type int[] to
immutable(int[])


 If code like that can't be accepted in future D/DMD versions, then I think DMD
should give an error message that explains why the r2 implicitly conversion is
not acceptable (while the implicitly conversion to r1  is acceptable).

 Bye,
 bearophile

This particular case should work, because there is no possibility parameters and return value alias. Have you already filed an enhancement request about this? However, as soon as it looks like this: Object[] foo3(const Object[] a) pure { // ... } Then it cannot compile when passed a mutable or const array anymore, whereas Object[] foo3(in Object[] a) pure { // ... } Should work even then (but preferably after DMD starts to actually enforce 'scope'). I think the best solution to that more general problem would be to allow 'inout' on the return value when it is not on a parameter. Another thing: This should always work: // T[] foo2(const T[]){...}; immutable T[] arr1 immutable T[] r3 = foo2(arr1); // currently error
Dec 21 2011
parent bearophile <bearophileHUGS lycos.com> writes:
Timon Gehr:

 This particular case should work, because there is no possibility 
 parameters and return value alias.

The good thing is that this case can be fully determined at compile-time. The bad thing is that increases the complexity of D purity for the programmer that has to use it.
 Have you already filed an enhancement 
 request about this?

I have not filed a diagnostic enhancement regarding the last part of my post, but I have filed an enhancement on the main problem. Sometimes design decisions need to be discussed here and not in Bugzilla. However, as soon as it looks like this:
 
 Object[] foo3(const Object[] a) pure {
      // ...
 }
 
 Then it cannot compile when passed a mutable or const array anymore, whereas
 
 Object[] foo3(in Object[] a) pure {
      // ...
 }
 
 Should work even then (but preferably after DMD starts to actually 
 enforce 'scope').

Nice.
 Another thing: This should always work:
 // T[] foo2(const T[]){...}; immutable T[] arr1
 immutable T[] r3 = foo2(arr1); // currently error

This is yet another situation, I think. Bye, bearophile
Dec 21 2011