www.digitalmars.com         C & C++   DMDScript  

digitalmars.D - Deprecated Nullable.get warning with Appenders

reply rbscott <tjonsies818 yahoo.com> writes:
Hello,

I was scratching my head with this warning for a while until I 
was able to figure out what was causing it. The repro case is 
pretty simple: (The challenge is the error doesn't point you to 
where the problem is occuring).

```
import std.array : appender, Appender;
import std.typecons : Nullable;

struct StructWithNullable {
     Nullable!(string) nullableString;
}

void main()
{
     Appender!(StructWithNullable[]) structWithNullableAppender;
     structWithNullableAppender.put(StructWithNullable.init);
}
```

On the playground this prints the following warnings:

```
/dlang/dmd/linux/bin64/../../src/phobos/std/traits.d(3688): 
Deprecation: function std.typecons.Nullable!string.Nullable.get_ 
is deprecated - Implicit conversion with alias Nullable.get this 
will be removed after 2.096. Please use .get explicitly.
/dlang/dmd/linux/bin64/../../src/phobos/std/traits.d(3689): 
Deprecation: function std.typecons.Nullable!string.Nullable.get_ 
is deprecated - Implicit conversion with alias Nullable.get this 
will be removed after 2.096. Please use .get explicitly.
```

I think this is something to do with the Appender library, but 
after looking into the logic for the put method, I couldn't wrap 
my head around what was wrong. Happy to help however possible. 
With some guidance, I could put together a PR for Appender.

thanks!
rbscott
Jan 30 2020
parent reply FeepingCreature <feepingcreature gmail.com> writes:
On Friday, 31 January 2020 at 01:13:41 UTC, rbscott wrote:
 Hello,

 I was scratching my head with this warning for a while until I 
 was able to figure out what was causing it. The repro case is 
 pretty simple: (The challenge is the error doesn't point you to 
 where the problem is occuring).

 ```
 import std.array : appender, Appender;
 import std.typecons : Nullable;

 struct StructWithNullable {
     Nullable!(string) nullableString;
 }

 void main()
 {
     Appender!(StructWithNullable[]) structWithNullableAppender;
     structWithNullableAppender.put(StructWithNullable.init);
 }
 ```

 On the playground this prints the following warnings:

 ```
 /dlang/dmd/linux/bin64/../../src/phobos/std/traits.d(3688): 
 Deprecation: function 
 std.typecons.Nullable!string.Nullable.get_ is deprecated - 
 Implicit conversion with alias Nullable.get this will be 
 removed after 2.096. Please use .get explicitly.
 /dlang/dmd/linux/bin64/../../src/phobos/std/traits.d(3689): 
 Deprecation: function 
 std.typecons.Nullable!string.Nullable.get_ is deprecated - 
 Implicit conversion with alias Nullable.get this will be 
 removed after 2.096. Please use .get explicitly.
 ```

 I think this is something to do with the Appender library, but 
 after looking into the logic for the put method, I couldn't 
 wrap my head around what was wrong. Happy to help however 
 possible. With some guidance, I could put together a PR for 
 Appender.

 thanks!
 rbscott
Could you file a bug report for this so I can make a fix PR please? I feel responsible, since I pushed for this deprecation and I really don't want it to be rolled back. But imo this is just part of the ongoing damage caused by `alias Nullable.get this`. Nullable!T has an assign overload for T. Nullable!T implicitly converts to T via `.get`. As such, Nullable!T can be assigned Nullable!T - in a way that is guaranteed to crash if Nullable is null, but it *can* be done! (And the compiler will do it silently by default.) Well, now `.get` is deprecated, so this hypothetical loop is also deprecated... but it still *compiles*. So by this metric, Nullable!T has an elaborate assign operation. It's a wrong and harmful assign operation, but to be fair it *is* elaborate as well. The solution is probably just to give `Nullable!T` an "official" assign overload for `Nullable!T` to overload-mask the `get-opAssign` loop entirely. Seems to remove the deprecation in tests.
Jan 30 2020
parent reply FeepingCreature <feepingcreature gmail.com> writes:
On Friday, 31 January 2020 at 07:16:49 UTC, FeepingCreature wrote:
 Nullable!T has an assign overload for T. Nullable!T implicitly 
 converts to T via `.get`. As such, Nullable!T can be assigned 
 Nullable!T - in a way that is guaranteed to crash if Nullable 
 is null, but it *can* be done! (And the compiler will do it 
 silently by default.) Well, now `.get` is deprecated, so this 
 hypothetical loop is also deprecated... but it still *compiles*.
Correction to avoid it seeming worse than it is: the compiler will not do this by default. The problem with hasElaborateAssign is that it calls opAssign manually. (There *were* bugs where the compiler did this by default though, when it thought that was the way to convert between constnesses for instance, but they're fixed.)
Jan 30 2020
parent drug <drug2004 bk.ru> writes:
On 1/31/20 10:32 AM, FeepingCreature wrote:
 On Friday, 31 January 2020 at 07:16:49 UTC, FeepingCreature wrote:
 Nullable!T has an assign overload for T. Nullable!T implicitly 
 converts to T via `.get`. As such, Nullable!T can be assigned 
 Nullable!T - in a way that is guaranteed to crash if Nullable is null, 
 but it *can* be done! (And the compiler will do it silently by 
 default.) Well, now `.get` is deprecated, so this hypothetical loop is 
 also deprecated... but it still *compiles*.
Correction to avoid it seeming worse than it is: the compiler will not do this by default. The problem with hasElaborateAssign is that it calls opAssign manually. (There *were* bugs where the compiler did this by default though, when it thought that was the way to convert between constnesses for instance, but they're fixed.)
See also https://forum.dlang.org/thread/znrvjuemkrstlascgmta forum.dlang.org
Jan 30 2020