Thread overview
Remove implicit non-zero initalization
5 days ago
Quirin Schroll
5 days ago
jmh530
5 days ago
Lance Bachmeier
5 days ago
Juraj
5 days ago
Nick Treleaven
4 days ago
Quirin Schroll
4 days ago
Quirin Schroll
5 days ago
Paul Backus
5 days ago

The initialization of variables with a type that has a non-zero init value has caused lots of bugs. Remove it. Variables of these types then require explicit initialization, as if they had @disable this().

char ch; // as if `= 0xFF`
double x; // as if `= double.nan`

Those would require an explicit initializer:

char ch0 = char.init; // okay
char ch1 = void; // okay

Almost no other language uses these initialization values.

Nothing will be lost if it’s done in a future edition.

5 days ago

On Wednesday, 15 October 2025 at 11:58:48 UTC, Quirin Schroll wrote:

>

The initialization of variables with a type that has a non-zero init value has caused lots of bugs. Remove it. Variables of these types then require explicit initialization, as if they had @disable this().

char ch; // as if `= 0xFF`
double x; // as if `= double.nan`

Those would require an explicit initializer:

char ch0 = char.init; // okay
char ch1 = void; // okay

Almost no other language uses these initialization values.

Nothing will be lost if it’s done in a future edition.

Generic code would need to remember to always use the explicit initialization. So you solve one problem and create another. You would need to remove all default initialization to make it consistent.

5 days ago

On Wednesday, 15 October 2025 at 11:58:48 UTC, Quirin Schroll wrote:

>

The initialization of variables with a type that has a non-zero init value has caused lots of bugs. Remove it. Variables of these types then require explicit initialization, as if they had @disable this().

char ch; // as if `= 0xFF`
double x; // as if `= double.nan`

Those would require an explicit initializer:

char ch0 = char.init; // okay
char ch1 = void; // okay

Almost no other language uses these initialization values.

Nothing will be lost if it’s done in a future edition.

This will make every templated type requiring explicit T.init
IMHO, not something Dlang user subscribed to.

5 days ago

On Wednesday, 15 October 2025 at 12:57:10 UTC, jmh530 wrote:

>

On Wednesday, 15 October 2025 at 11:58:48 UTC, Quirin Schroll wrote:

>

The initialization of variables with a type that has a non-zero init value has caused lots of bugs. Remove it. Variables of these types then require explicit initialization, as if they had @disable this().

char ch; // as if `= 0xFF`
double x; // as if `= double.nan`

Those would require an explicit initializer:

char ch0 = char.init; // okay
char ch1 = void; // okay

Almost no other language uses these initialization values.

Nothing will be lost if it’s done in a future edition.

Generic code would need to remember to always use the explicit initialization. So you solve one problem and create another. You would need to remove all default initialization to make it consistent.

I think a flag --explicit-initialization would be very helpful. This is an example where the complexity of generic code spills over to make the language quite hostile. At least give the rest of us a way to opt out of the pain.

5 days ago

On Wednesday, 15 October 2025 at 11:58:48 UTC, Quirin Schroll wrote:

>

The initialization of variables with a type that has a non-zero init value has caused lots of bugs. Remove it. Variables of these types then require explicit initialization, as if they had @disable this().

So, we have a language feature that sometimes causes bugs, and we're going to fix it with a change that will always break code?

I agree that non-zero init values are weird and unintuitive, but I don't see how the benefits here can possibly justify the (enormous) costs.

5 days ago

On Wednesday, 15 October 2025 at 12:58:01 UTC, Juraj wrote:

>

This will make every templated type requiring explicit T.init

T.init isn't valid for a nested struct, and T() isn't valid when static opCall is defined (see https://forum.dlang.org/post/mailman.32.1760364841.3501.digitalmars-d-learn@puremagic.com).

Phobos 3 has defaultInit, but that doesn't work for nested structs:

    // defaultInit doesn't have access to this scope and thus cannot
    // initialize the nested struct.
    static assert(!__traits(compiles, defaultInit!Nested));

https://github.com/dlang/phobos/pull/10842

4 days ago

On Wednesday, 15 October 2025 at 18:04:07 UTC, Nick Treleaven wrote:

>

On Wednesday, 15 October 2025 at 12:58:01 UTC, Juraj wrote:

>

This will make every templated type requiring explicit T.init

T.init isn't valid for a nested struct, and T() isn't valid when static opCall is defined (see https://forum.dlang.org/post/mailman.32.1760364841.3501.digitalmars-d-learn@puremagic.com).

Phobos 3 has defaultInit, but that doesn't work for nested structs:

    // defaultInit doesn't have access to this scope and thus cannot
    // initialize the nested struct.
    static assert(!__traits(compiles, defaultInit!Nested));

https://github.com/dlang/phobos/pull/10842

I’m wondering why we can’t just have default(T). Essentially, it would do what defaultInit!T does, but without the limitations for nested types.

auto x = default(T);
T x = default; // alternative for variable initializers
f(default(T)); // call `f` with a default-initialized value of `T`
4 days ago

On Thursday, 16 October 2025 at 17:45:34 UTC, Quirin Schroll wrote:

>

On Wednesday, 15 October 2025 at 18:04:07 UTC, Nick Treleaven wrote:

>

On Wednesday, 15 October 2025 at 12:58:01 UTC, Juraj wrote:

>

This will make every templated type requiring explicit T.init

T.init isn't valid for a nested struct, and T() isn't valid when static opCall is defined (see https://forum.dlang.org/post/mailman.32.1760364841.3501.digitalmars-d-learn@puremagic.com).

Phobos 3 has defaultInit, but that doesn't work for nested structs:

    // defaultInit doesn't have access to this scope and thus cannot
    // initialize the nested struct.
    static assert(!__traits(compiles, defaultInit!Nested));

https://github.com/dlang/phobos/pull/10842

I’m wondering why we can’t just have default(T). Essentially, it would do what defaultInit!T does, but without the limitations for nested types.

auto x = default(T);
T x = default; // alternative for variable initializers
f(default(T)); // call `f` with a default-initialized value of `T`

Thinking about it, T x = default; is just T x; and the implementation of default(T) can be a lowering to an immediately invoked lambda {T x; return x;}(), or, since the DMD internals support it, (T x, x). There is really no reason that this is a library feature.