>> But there is one trouble.

I don't see the trouble.

struct Foo
{
    int[] arr;
    this()//can be interpreted at compile time
    {
       arr = new int[3];
       arr[0] = 1;
       arr[1] = 2;
       arr[2] = 3;
    }
}
semantically, all new instances of Foo must get separate instance of array.
Foo f1;
Foo f2;
assert(f1.arr.ptr !is f2.arr.ptr); //expects put FAILS 

We should have assert(f1.arr.ptr is f2.arr.ptr); as well as assert(f1 is f2); which is consistent with having Foo.init be known at compile time ( we have physical equality, not just logical equality). There's no way around that.

So the only question is whether to call the default constructor as static this() or this() (with implicitly knowing that it should be callable at compile time). I think static this() makes it clearer.






On Fri, May 17, 2013 at 4:07 PM, Igor Stepanov <wazar.leollone@yahoo.com> wrote:
On Friday, 17 May 2013 at 22:45:01 UTC, Timothee Cour wrote:
Although I agree that having a default constructor would be convenient, I
think the problem is that S.init should be known at compile time by the
spec.

Maybe we could support the following syntax, with a static this instead of
this :

struct S
{
    int x=11;
    int y = void;

    static this()  // hypothetical

    {
        // x would already be initialized to int.init here
        assert(x == int.init);
        // y is left uninitialized here
       y=x*x;
    }
}

On Fri, May 17, 2013 at 2:34 PM, Andrej Mitrovic <andrej.mitrovich@gmail.com
wrote:

On 5/17/13, Walter Bright <walter@digitalmars.com> wrote:
> I oppose this. D has a lot of nice features because of the > .init
property.
> Default constructors wreck that.

Would they? I'm thinking the process would be:

struct S
{
    int x;
    int y = void;

    this()  // hypothetical
    {
        // x would already be initialized to int.init here
        assert(x == int.init);

        // y is left uninitialized here
    }
}

Maybe that's already clear. But why is .init actually such a big
problem? If it becomes arbitrarily expensive to call .init of a
struct, well it's because it has to be - if the user really provided
an expensive default ctor. But it's entirely the user's
responsibility. So then .init can even throw, but throwing exceptions
isn't a big deal. Is there some other problem?

A custom default ctor in a struct is one of the most asked for
features. Just yesterday we spent several hours explaining to a C++
user why a default ctor doesn't work, and what .init is for. The whole
conversation could have been avoided if D had support for custom
default ctors for structs. This topic comes up very often in IRC and
the forums.

May be we can allow default ctor, but ensure that it can be
interpreted at compile time and initialize .init value with
ctored value?
Foo.init = Foo(); //somewhere in deep of compiler

But there is one trouble.

struct Foo
{
    int[] arr;
    this()//can be interpreted at compile time
    {
       arr = new int[3];
       arr[0] = 1;
       arr[1] = 2;
       arr[2] = 3;
    }
}

semantically, all new instances of Foo must get separate instance
of array.

Foo f1;
Foo f2;
assert(f1.arr.ptr !is f2.arr.ptr); //expects put FAILS

However, if Foo.init initialized by compiler with Foo() and f1
and f2 will be initialized with Foo.init, f1.arr and f2.arr will
be the same value.

We can also restrict creating of any mutable reference instances
in this() constructor:

struct Foo
{
    int[] arr;
    immutable int[] arr2;
    this()//can be interpreted at compile time
    {
       arr = new int[3]; //NG
       arr = [1,2,3]; //NG
       arr2 = [1,2,3]; //OK, because arr2 is immutable and all
instances of foo can contains an single array instance

    }
}

But this way is so difficult and isn't much profitable.