DIP 1017--Add Bottom Type--Final Review
Johannes Loher
johannesloher at fg4f.de
Fri Jan 18 00:32:08 UTC 2019
Am 18.01.19 um 01:17 schrieb H. S. Teoh:
>
> Well, void* is simply a bad name for Any*, where Any is the top type.
> Even if we fix void* by renaming it to Any* (so that `void*` actually
> means a pointer to a unit type, whatever we decide that would be), we
> still have the problem of the chain of implicit conversions:
>
> void --> TBottom* --> Any*
>
> so as long as you define void == TBottom*, you have the weirdness:
>
> void procedure(...) {}
> Any* ptr = procedure();
> // subsequent fun with casting and dereferencing ptr.
>
> This is why I don't think we should define void == TBottom*, even though
> both are ostensibly unit types. Besides, following the same logic, one
> would have to conclude typeof(null) == void too (since typeof(null) also
> only contains a single value), which leads to other weird situations.
I actually think this is ok. I don't reall have an issue with it. But I
am also not convinced that we _need_ to do it that way. As I mentioned
ealier, Kotlin for example does not do this (you have to replace
pointers with optional types). They have distinct `Unit` and `Nothing?`
types and this is fine in my opinion.
On the other hand, I definitely think we should make `Tbottom* ==
typeof(null)`.
>
> Anyway, you brought up an excellent point that D's types are not
> structural types. So perhaps pointers, including TBottom*, aren't as
> simple as we thought they were. Perhaps we could analyze pointers as
> having an implicit (and unrepresented) component identifying themselves
> as a pointer type, in addition to holding the pointer value itself. If
> you will, they're a product type of an atomic isPointer object with the
> pointer value to their specified type. So TBottom* isn't the same as
> the real unit type, which conveys no information; it (implicitly)
> conveys the information that it is a pointer, so it may be distinguished
> from the unit type as being the product of isPointer with Unit, not just
> Unit itself.
>
> Then we can still define void as the unit type, and TBottom* would be a
> distinct type that always has the (explicit) value null (with an
> associated implicit isPointer attribute). Dereferencing TBottom* would
> then be identical to dereferencing null, which should cause a runtime
> abort.
>
> (And similarly, empty structs would not be true unit types either, but
> product types of their names with the types of their fields. True
> product types in the type theoretic sense would have to be anonymous
> structs or entities like std.typecons.Tuple.)
>
> Or alternatively, we can think of TBottom* as a *decorated* type
> (decorated with isPointer or TBottom as the type of its target) that is
> to be distinguished from the (undecorated) true unit type. Similarly
> with named empty structs.
>
>
> T
>
This sounds very reasonable.
More information about the Digitalmars-d
mailing list