On Monday, April 16, 2018 08:34:13 FeepingCreature via Digitalmars-d wrote: > I think `alias get this` is a misfeature. > > If at all possible, compiletime errors should be preferred over > runtime errors. The point of Nullable is that the value contained > within may be absent. Considering the prevalence of type > inference and UFCS chaining in idiomatic D, it is very possible > that a change to a Nullable type, or a change of a parameter to a > non-Nullable type, may not be noticed by the typesystem. In that > case, the unhandled null state that could have been caught by the > compiler will turn into a runtime exception. > > This seems a poor, magical and unexpected choice of behavior. > > Is there any strong reason why Nullable!T can implicitly convert > to T? If not, I'd argue that `alias get this` should be > deprecated, and removed at the earliest convenience. It throws > away clear safety for unclear gain.
I think that the whole point of the alias this was to try and make it so that code could treat Nullable!T as T if it didn't care about the difference - and plenty of code has no need to, especially if code above it already guaranteed that it has a value. I don't think that that's necessarily unreasonable and don't see anything unsafe or buggy about it. However, on some level, the whole idea of treating Nullable!T as T in code that doesn't need to check for null falls flat on its face thanks to the fact that we don't have implicit construction in D. So, if you have something like auto foo(Nullable!int i) { ... } you can't pass it 42. You're forced to do something like Nullable!int(42) or nullable(42). I've found that to frequently be annoying when a function returns a Nullable. Ideally, the differences between Nullable!T and T would only be visible when get or some other member function on Nullable was called, and the alias this helps with that, but it really doesn't fix it. And actually, even if we had implicit construction, it still wouldn't be enough, because alias this isn't used with template instantiations, and we don't currently have a way in the language to say that it should be. Without that, any templates that accepts T won't work with Nullable!T unless they accept implicit conversions to T (which usually a bad idea with templates). To really act like a T, Nullable!T would need to instantiate templates with T rather than Nullable!T (at least by default). So, we'd need several language changes in order to be able to have code treat Nullable!T the same as T except when it actually cared, and as such, the alias this on Nullable arguably doesn't achieve its goal. It just solves one piece of the puzzle and then causes frustration when it doesn't solve the others. I don't know if the frustration would go up or down if it didn't attempt to solve the problem at all and Nullable had no implicit conversion. In any case, given that a Nullable!T really can't masquerade as a T in general, I don't know how valuable the alias this really is, and I'm not sure that I care whether it's there or not, but I fail to understand why it's actually a problem. I don't follow how this has anything to do with the type system or making anything safer. You don't get any more or fewer null checks with foo(i.get); than foo(i); The code is the same except for the fact that in the second case, the call to get is invisible. As such, all I see that you lose is that the programmer can't necessarily immediately see that i is a Nullable!T instead of a T. I can see why that might be undesirable for some folks, but I don't see why it would be a safety problem. And given that we already have alias this on Nullable, we need a reason for getting rid of it, not a reason for why it would be useful to have. I think that you need a more concrete reason as to why this is a problem other than it's too "magical." And you may have such a reason, but I don't see it clearly stated here. - Jonathan M Davis