www.digitalmars.com         C & C++   DMDScript  

digitalmars.D - DIP 1017--Add Bottom Type--Community Review Round 1

reply Mike Parker <aldacron gmail.com> writes:
This is the feedback thread for the first round of Community 
Review for DIP 1017, "Add Bottom Type":

https://github.com/dlang/DIPs/blob/8274b0f600075e4553b41c31f4b77be2d917bb40/DIPs/DIP1017.md

All review-related feedback on and discussion of the DIP should 
occur in this thread. The review period will end at 11:59 PM ET 
on August 24, or when I make a post declaring it complete.

At the end of Round 1, if further review is deemed necessary, the 
DIP will be scheduled for another round. Otherwise, it will be 
queued for the Final Review and Formal Assessment by the language 
maintainers.

Please familiarize yourself with the documentation for the 
Community Review before participating.

https://github.com/dlang/DIPs/blob/master/PROCEDURE.md#community-review

Thanks in advance to all who participate.
Aug 08 2018
next sibling parent reply Nicholas Wilson <iamthewilsonator hotmail.com> writes:
On Thursday, 9 August 2018 at 03:02:55 UTC, Mike Parker wrote:
 This is the feedback thread for the first round of Community 
 Review for DIP 1017, "Add Bottom Type":

 https://github.com/dlang/DIPs/blob/8274b0f600075e4553b41c31f4b77be2d917bb40/DIPs/DIP1017.md

 All review-related feedback on and discussion of the DIP should 
 occur in this thread. The review period will end at 11:59 PM ET 
 on August 24, or when I make a post declaring it complete.

 At the end of Round 1, if further review is deemed necessary, 
 the DIP will be scheduled for another round. Otherwise, it will 
 be queued for the Final Review and Formal Assessment by the 
 language maintainers.

 Please familiarize yourself with the documentation for the 
 Community Review before participating.

 https://github.com/dlang/DIPs/blob/master/PROCEDURE.md#community-review

 Thanks in advance to all who participate.
All of my points made in the draft review still stand, i.e. that this should be an attribute or pragma. Note that this feature is already supported by LDC as an attribute. The benefit that this DIP provides are: "documentation" (rationale point 2) and optimisation (rationale points 1 & 4). The claim made by Point 3 is dubious and unsubstantiated at best. Rationale point 2 comes in the form of rendered documentation and the source code. Rendered documentation, regardless of the form used should be able to convey that a function does not return. Reading the source it should be easily determinable that a function does not return, use of an suitably named attribute or pragma (i.e. pragma (noreturn) or noreturn) makes it immediately obvious. Returning a type named "Tbottom" absolutely does not, "never_t" as suggested in the draft review is better but is not strictly better than an attribute or pragma but, IMO is still worse. The optimisation benefits provided by dead code elimination may be significant, but again this information is equally well conveyed to the compiler by an attribute or pragma. The hardcoded list of symbols, will provide the vast majority of those gains so extending this to user code will provide very marginal benefit, especially with a aggressively optimising compiler (e.g. LDC, GDC) that will propagate that information anyway. The downsides of this DIP are the breaking changes and unneeded complexity. Generic code that checks `is(T==void)` or `is(ReturnType!F == void)` will break, as will code that uses the return value of a function that happens to be inferred to return no type, use of the ternary ?: will now no longer always be the common type of the second and third operands. The complexity will manifest itself as making error messages more confusing, making the learning curve steeper than it needs to be and the implementation. The DIP makes the claim that: * "[ noreturn] has the awkward result of a function specifying it has a return type T, but never returns that type". When it is deliberate (such as annotating a fatal error function) the is almost exclusively `void` (I know of no examples to the contrary). * "[With noreturn] other potential uses of a bottom type will not be expressible". What other? Documentation and optimisation definitely can be, the are in LDC since a long time, there are no other substantiated benefits listed in the DIP. If this DIP were to make the claim that type inference and propagation would catch bugs, then perhaps it would make more sense than an attribute or pragma, but it would have to be convincing that resulting code breakage would be worth it.
Aug 08 2018
next sibling parent reply Andrea Fontana <nospam example.com> writes:
On Thursday, 9 August 2018 at 04:10:47 UTC, Nicholas Wilson wrote:
 The DIP makes the claim that:
  * "[ noreturn] has the awkward result of a function specifying 
 it has a return type T, but never returns that type". When it 
 is deliberate (such as annotating a fatal error function) the 
 is almost exclusively `void` (I know of no examples to the 
 contrary).
Let's say we need to implement an interface with a int func(); member. We can mark it with noreturn but we can't use TBottom return type: we're going to break interface implementation. Andrea
Aug 09 2018
parent reply w0rp <devw0rp gmail.com> writes:
On Thursday, 9 August 2018 at 10:37:36 UTC, Andrea Fontana wrote:
 On Thursday, 9 August 2018 at 04:10:47 UTC, Nicholas Wilson 
 wrote:
 The DIP makes the claim that:
  * "[ noreturn] has the awkward result of a function 
 specifying it has a return type T, but never returns that 
 type". When it is deliberate (such as annotating a fatal error 
 function) the is almost exclusively `void` (I know of no 
 examples to the contrary).
Let's say we need to implement an interface with a int func(); member. We can mark it with noreturn but we can't use TBottom return type: we're going to break interface implementation. Andrea
It will work, and why it will work requires some understanding of bottom types. You can define the function as `TBottom func()` and it should work, because `TBottom` is a subtype of `int`. In the same way you can implement `ParentClass func()` as `SubClass func()`, because `SubClass` is a subtype of `ParentClass`. Similarly, you can assign values of `TBottom` to `int`, because `TBottom` is a subtype of all types, but you cannot assign `int` to `TBottom`, because `int` is not a subtype of `TBottom`.
Aug 09 2018
parent reply Andrea Fontana <nospam example.com> writes:
On Thursday, 9 August 2018 at 15:56:31 UTC, w0rp wrote:
 On Thursday, 9 August 2018 at 10:37:36 UTC, Andrea Fontana 
 wrote:
 On Thursday, 9 August 2018 at 04:10:47 UTC, Nicholas Wilson 
 wrote:
 The DIP makes the claim that:
  * "[ noreturn] has the awkward result of a function 
 specifying it has a return type T, but never returns that 
 type". When it is deliberate (such as annotating a fatal 
 error function) the is almost exclusively `void` (I know of 
 no examples to the contrary).
Let's say we need to implement an interface with a int func(); member. We can mark it with noreturn but we can't use TBottom return type: we're going to break interface implementation. Andrea
It will work, and why it will work requires some understanding of bottom types. You can define the function as `TBottom func()` and it should work, because `TBottom` is a subtype of `int`. In the same way you can implement `ParentClass func()` as `SubClass func()`, because `SubClass` is a subtype of `ParentClass`. Similarly, you can assign values of `TBottom` to `int`, because `TBottom` is a subtype of all types, but you cannot assign `int` to `TBottom`, because `int` is not a subtype of `TBottom`.
is(T == int) will work with T==tbottom too? is(T:int) ? I feel that all this things are going to complicate implementation and add corner cases, but maybe I'm wrong... Andrea
Aug 09 2018
parent reply Petar Kirov [ZombineDev] <petar.p.kirov gmail.com> writes:
On Friday, 10 August 2018 at 06:44:20 UTC, Andrea Fontana wrote:
 On Thursday, 9 August 2018 at 15:56:31 UTC, w0rp wrote:
 On Thursday, 9 August 2018 at 10:37:36 UTC, Andrea Fontana 
 wrote:
 On Thursday, 9 August 2018 at 04:10:47 UTC, Nicholas Wilson 
 wrote:
 The DIP makes the claim that:
  * "[ noreturn] has the awkward result of a function 
 specifying it has a return type T, but never returns that 
 type". When it is deliberate (such as annotating a fatal 
 error function) the is almost exclusively `void` (I know of 
 no examples to the contrary).
Let's say we need to implement an interface with a int func(); member. We can mark it with noreturn but we can't use TBottom return type: we're going to break interface implementation. Andrea
It will work, and why it will work requires some understanding of bottom types. You can define the function as `TBottom func()` and it should work, because `TBottom` is a subtype of `int`. In the same way you can implement `ParentClass func()` as `SubClass func()`, because `SubClass` is a subtype of `ParentClass`. Similarly, you can assign values of `TBottom` to `int`, because `TBottom` is a subtype of all types, but you cannot assign `int` to `TBottom`, because `int` is not a subtype of `TBottom`.
is(T == int) will work with T==tbottom too? is(T:int) ? I feel that all this things are going to complicate implementation and add corner cases, but maybe I'm wrong... Andrea
`is(T == U)` evaluates to true iff `T` is exactly `U`. `is(T : U)` tests if `T` is a subtype of (can be implicitly converted to) `U` [0]. So we have: `is(typeof(assert(0)) == T)` is false, unless `T` is `typeof(assert(0))` `is(typeof(assert(0)) : T)` is always true (as bottom is implicitly convertible to any other type, including itself). [0]: https://dlang.org/spec/expression#is_expression
Aug 10 2018
parent reply Andrea Fontana <nospam example.com> writes:
On Friday, 10 August 2018 at 07:01:09 UTC, Petar Kirov 
[ZombineDev] wrote:
 `is(T == U)` evaluates to true iff `T` is exactly `U`. `is(T : 
 U)` tests if `T` is a subtype of (can be implicitly converted 
 to) `U` [0]. So we have:

 `is(typeof(assert(0)) == T)` is false, unless `T` is 
 `typeof(assert(0))`
 `is(typeof(assert(0)) : T)` is always true (as bottom is 
 implicitly convertible to any other type, including itself).

 [0]: https://dlang.org/spec/expression#is_expression
So if I need to write something like: void callback(alias T)() if(is(ReturnType!T == int)) { } I have to change it to: void callback(alias T)() if(is(ReturnType!T == int) || is(ReturnType!T == typeof(assert(0))) { } ?
Aug 10 2018
parent Petar Kirov [ZombineDev] <petar.p.kirov gmail.com> writes:
On Friday, 10 August 2018 at 07:19:02 UTC, Andrea Fontana wrote:
 On Friday, 10 August 2018 at 07:01:09 UTC, Petar Kirov 
 [ZombineDev] wrote:
 `is(T == U)` evaluates to true iff `T` is exactly `U`. `is(T : 
 U)` tests if `T` is a subtype of (can be implicitly converted 
 to) `U` [0]. So we have:

 `is(typeof(assert(0)) == T)` is false, unless `T` is 
 `typeof(assert(0))`
 `is(typeof(assert(0)) : T)` is always true (as bottom is 
 implicitly convertible to any other type, including itself).

 [0]: https://dlang.org/spec/expression#is_expression
So if I need to write something like: void callback(alias T)() if(is(ReturnType!T == int)) { } I have to change it to: void callback(alias T)() if(is(ReturnType!T == int) || is(ReturnType!T == typeof(assert(0))) { } ?
No. That's the point - you don't have to change anything.
Aug 10 2018
prev sibling parent reply Dukc <ajieskola gmail.com> writes:
On Thursday, 9 August 2018 at 04:10:47 UTC, Nicholas Wilson wrote:
 * "[With  noreturn] other potential uses of a bottom type will 
 not be expressible". What other? Documentation and optimisation 
 definitely can be, the are in LDC since a long time, there are 
 no other substantiated benefits listed in the DIP.
One example comes to mind: is(typeof(null) == typeof(assert(0))).
Aug 10 2018
parent reply Dukc <ajieskola gmail.com> writes:
On Friday, 10 August 2018 at 11:28:38 UTC, Dukc wrote:
 One example comes to mind: is(typeof(null) == 
 typeof(assert(0))).
meant is(typeof(*null) == typeof(assert(0)))
Aug 10 2018
parent reply Nicholas Wilson <iamthewilsonator hotmail.com> writes:
On Friday, 10 August 2018 at 11:31:02 UTC, Dukc wrote:
 On Friday, 10 August 2018 at 11:28:38 UTC, Dukc wrote:
 One example comes to mind: is(typeof(null) == 
 typeof(assert(0))).
meant is(typeof(*null) == typeof(assert(0)))
How is that a good thing??? Also that is not specified in the dip. I would expect that to fail because both will produce error nodes in the AST, only assert(0) is considered special under this DIP.
Aug 10 2018
parent reply Dukc <ajieskola gmail.com> writes:
On Friday, 10 August 2018 at 12:42:37 UTC, Nicholas Wilson wrote:
 meant is(typeof(*null) == typeof(assert(0)))
How is that a good thing??? Also that is not specified in the dip. I would expect that to fail because both will produce error nodes in the AST, only assert(0) is considered special under this DIP.
Granted, an example like that should be described so we know better what he means with the possible future uses. The benefit would be that null can be a regular pointer constant (enum null = typeof(&assert(false)).init) instead of a symbol with special meaning. I'd think it makes compiler rules less complex. Another advantage is that you could pass null as an argument for a function template which wants to know it's element type (but of course not instantiate it) like any other pointer.
Aug 10 2018
next sibling parent reply Stefan Koch <uplink.coder googlemail.com> writes:
On Friday, 10 August 2018 at 13:15:46 UTC, Dukc wrote:
 On Friday, 10 August 2018 at 12:42:37 UTC, Nicholas Wilson 
 wrote:
 meant is(typeof(*null) == typeof(assert(0)))
How is that a good thing??? Also that is not specified in the dip. I would expect that to fail because both will produce error nodes in the AST, only assert(0) is considered special under this DIP.
Granted, an example like that should be described so we know better what he means with the possible future uses. The benefit would be that null can be a regular pointer constant (enum null = typeof(&assert(false)).init) instead of a symbol with special meaning. I'd think it makes compiler rules less complex. Another advantage is that you could pass null as an argument for a function template which wants to know it's element type (but of course not instantiate it) like any other pointer.
No that cant be happing, retuning null is still returning something. as opposed to not returning.
Aug 10 2018
parent reply Timon Gehr <timon.gehr gmx.ch> writes:
On 11.08.2018 01:40, Stefan Koch wrote:
 Another advantage is that you could pass null as an argument for a 
 function template which wants to know it's element type (but of course 
 not instantiate it) like any other pointer.
No that cant be happing, retuning null is still returning something. as opposed to not returning.
I think you misunderstood. His point was that this could work: void foo(T)(T* ptr){} void main(){ foo(null); }
Aug 10 2018
parent Stefan Koch <uplink.coder googlemail.com> writes:
On Saturday, 11 August 2018 at 00:01:34 UTC, Timon Gehr wrote:
 On 11.08.2018 01:40, Stefan Koch wrote:
 Another advantage is that you could pass null as an argument 
 for a function template which wants to know it's element type 
 (but of course not instantiate it) like any other pointer.
No that cant be happing, retuning null is still returning something. as opposed to not returning.
I think you misunderstood. His point was that this could work: void foo(T)(T* ptr){} void main(){ foo(null); }
Ah yes ... Thanks! (also I should not ignore the grammar/spell checker)
Aug 10 2018
prev sibling parent reply Nicholas Wilson <iamthewilsonator hotmail.com> writes:
On Friday, 10 August 2018 at 13:15:46 UTC, Dukc wrote:
 The benefit would be that null can be a regular pointer 
 constant (enum null = typeof(&assert(false)).init) instead of a 
 symbol with special meaning. I'd think it makes compiler rules 
 less complex.
I disagree.
 Another advantage is that you could pass null as an argument 
 for a function template which wants to know it's element type 
 (but of course not instantiate it) like any other pointer.
Of what _practical use_ is that?
Aug 11 2018
parent Dukc <ajieskola gmail.com> writes:
On Saturday, 11 August 2018 at 10:04:14 UTC, Nicholas Wilson 
wrote:
 On Friday, 10 August 2018 at 13:15:46 UTC, Dukc wrote:
 The benefit would be that null can be a regular pointer 
 constant (enum null = typeof(&assert(false)).init) instead of 
 a symbol with special meaning. I'd think it makes compiler 
 rules less complex.
I disagree.
I have no doubt you know more about compiler internals than me so not arguing about that.
 Another advantage is that you could pass null as an argument 
 for a function template which wants to know it's element type 
 (but of course not instantiate it) like any other pointer.
Of what _practical use_ is that?
Tried to come up with an example but it would be so far-fetched that it won't be a reason in itself to add a new feature. I have to start to think longer before I post.
Aug 13 2018
prev sibling next sibling parent reply Uknown <sireeshkodali1 gmail.com> writes:
I would like to point out that C++ does this with attributes 
instead[0]. If this was an attribute instead (like ` noreturn`), 
it would simplify interfacing with C++. It would also avoid the 
breaking change.

[0]: eel.is/c++draft/DCL.attral.noreturn
Aug 08 2018
parent Dominikus Dittes Scherkl <dominikus.scherkl continental-corporation.com> writes:
On Thursday, 9 August 2018 at 04:16:45 UTC, Uknown wrote:
 I would like to point out that C++ does this with attributes 
 instead[0]. If this was an attribute instead (like 
 ` noreturn`), it would simplify interfacing with C++. It would 
 also avoid the breaking change.

 [0]: eel.is/c++draft/DCL.attral.noreturn
The DIP mentions that, (e.g. I also don't like the syntax " noreturn int fun()"), but I don't understand what "other uses" of a type tBottom there are, which the DIP states are not possible in C++. Especially I want a section that explains how tBottom is different from void in such situations. For functions that don't return it's clear, but else?
Aug 09 2018
prev sibling next sibling parent reply Stefan Koch <uplink.coder googlemail.com> writes:
On Thursday, 9 August 2018 at 03:02:55 UTC, Mike Parker wrote:
 This is the feedback thread for the first round of Community 
 Review for DIP 1017, "Add Bottom Type":

 [ ... ]
Regarding the rationale: It should be pointed out that this is a further complication of the type-system (which is already more complex than what c++ has). That does impact generic code. My own experience with generic code has show that it is very hard (practically impossible) to write correct code, (correct meaning here working as intended, when instantiation succeeds) even when using template constraints. There is no explanation of when the additional optimizations would be actually relevant, Usually functions that don't return abort the program anyway. There not even an example piece of code where the newly enabled optimizations would make an impact. The point about other system languages having this feature is actually the most substantiated one :) I could accept a rationale which is about being able to simplify and extend the applicability of CFA (control flow analysis). Though even than CFA, not really that effective when is comes to making faster code. It is however quite good at subtly breaking code :( TLDR; I would kindly recommend further expansion on the interactions with the rest of the language and implications thereof.. Regards, Stefan
Aug 09 2018
next sibling parent Nicholas Wilson <iamthewilsonator hotmail.com> writes:
On Thursday, 9 August 2018 at 10:47:37 UTC, Stefan Koch wrote:
 Regarding the rationale:

 It should be pointed out that this is a further complication of 
 the type-system (which is already more complex than what c++ 
 has).
 That does impact generic code.

 My own experience with generic code has show that it is very 
 hard (practically impossible) to write correct code,
 (correct meaning here working as intended, when instantiation 
 succeeds) even when using template constraints.
Indeed.
 There is no explanation of when the additional optimizations 
 would be actually relevant,
 Usually functions that don't return abort the program anyway.
I presume Walter is talking about considering all branches that don't return to be cold and "outlining" them as much as possible so as to not pollute icache, which he already implemented. So I assume he's talking about propagating that information?
 There not even an example piece of code where the newly enabled 
 optimizations would make an impact.

 The point about other system languages having this feature is 
 actually the most substantiated one :)
It was about that is was required to be competitive which I find to be a bizarre claim. But we already have this in LDC, GDC probably has something similar (whatever corresponds to __attribute__(noreturn)),and if you care about perf you are not using DMD.
Aug 09 2018
prev sibling parent Kagamin <spam here.lot> writes:
On Thursday, 9 August 2018 at 10:47:37 UTC, Stefan Koch wrote:
 There is no explanation of when the additional optimizations 
 would be actually relevant,
 Usually functions that don't return abort the program anyway.
Maybe total code size. OT: as for microoptimizations, what bugged me is a pattern when a method returns its first argument to enable chaining, if it returned void (or something like that) and the chained call reused the first argument of the preceding call how much that can save? But indeed introspection can be painful.
Aug 09 2018
prev sibling next sibling parent 12345swordy <alexanderheistermann gmail.com> writes:
On Thursday, 9 August 2018 at 03:02:55 UTC, Mike Parker wrote:
 This is the feedback thread for the first round of Community 
 Review for DIP 1017, "Add Bottom Type":

 [...]
How does this DIP interact with constructors and deconstructors as they are glorified void functions? -Alexander
Aug 09 2018
prev sibling next sibling parent reply bachmeier <no spam.net> writes:
On Thursday, 9 August 2018 at 03:02:55 UTC, Mike Parker wrote:
 This is the feedback thread for the first round of Community 
 Review for DIP 1017, "Add Bottom Type":
I hope there is a better name than Tbottom. A name like that is not consistent with the rest of the language. Why not Bottom?
Aug 09 2018
next sibling parent reply Stefan Koch <uplink.coder googlemail.com> writes:
On Thursday, 9 August 2018 at 13:42:57 UTC, bachmeier wrote:
 On Thursday, 9 August 2018 at 03:02:55 UTC, Mike Parker wrote:
 This is the feedback thread for the first round of Community 
 Review for DIP 1017, "Add Bottom Type":
I hope there is a better name than Tbottom. A name like that is not consistent with the rest of the language. Why not Bottom?
according to the DIP, the name can be chosen arbitrarily as the type is retrieved via matching the type expression `typeof(assert(0))`
Aug 09 2018
parent bachmeier <no spam.net> writes:
On Thursday, 9 August 2018 at 13:45:54 UTC, Stefan Koch wrote:

 I hope there is a better name than Tbottom. A name like that 
 is not consistent with the rest of the language. Why not 
 Bottom?
according to the DIP, the name can be chosen arbitrarily as the type is retrieved via matching the type expression `typeof(assert(0))`
Okay. That's a lot worse. A type for a function that returns nothing and has an arbitrary name.
Aug 09 2018
prev sibling parent reply Gary Willoughby <dev nomad.uk.net> writes:
On Thursday, 9 August 2018 at 13:42:57 UTC, bachmeier wrote:
 On Thursday, 9 August 2018 at 03:02:55 UTC, Mike Parker wrote:
 This is the feedback thread for the first round of Community 
 Review for DIP 1017, "Add Bottom Type":
I hope there is a better name than Tbottom. A name like that is not consistent with the rest of the language. Why not Bottom?
`bottom_t` or `never_t` are much better but perhaps this should actually be an attribute ` bottom`, or more a documenting: ` noreturn`?
Aug 09 2018
parent bachmeier <no spam.net> writes:
On Thursday, 9 August 2018 at 13:56:05 UTC, Gary Willoughby wrote:

 perhaps this should actually be an attribute ` bottom`, or more 
 a documenting: ` noreturn`?
Yes, it should.
Aug 09 2018
prev sibling next sibling parent reply w0rp <devw0rp gmail.com> writes:
A better name for this type is `never`, which is the name of the 
TypeScript type with similar semantics. 
https://www.typescriptlang.org/docs/handbook/basic-types.html#never `nothing`
is also a decent name, used in some other languages, but `never` makes it more
obvious that a function never returns, and isn't as easy to confuse with
`void`, which is a different kind of nothing.
Aug 09 2018
parent reply docandrew <x x.com> writes:
On Thursday, 9 August 2018 at 15:50:02 UTC, w0rp wrote:
 A better name for this type is `never`, which is the name of 
 the TypeScript type with similar semantics. 
 https://www.typescriptlang.org/docs/handbook/basic-types.html#never `nothing`
is also a decent name, used in some other languages, but `never` makes it more
obvious that a function never returns, and isn't as easy to confuse with
`void`, which is a different kind of nothing.
+1 for "never" - it's descriptive and readable. -Jon
Aug 10 2018
next sibling parent Arun Chandrasekaran <aruncxy gmail.com> writes:
On Saturday, 11 August 2018 at 05:01:50 UTC, docandrew wrote:
 On Thursday, 9 August 2018 at 15:50:02 UTC, w0rp wrote:
 A better name for this type is `never`, which is the name of 
 the TypeScript type with similar semantics. 
 https://www.typescriptlang.org/docs/handbook/basic-types.html#never `nothing`
is also a decent name, used in some other languages, but `never` makes it more
obvious that a function never returns, and isn't as easy to confuse with
`void`, which is a different kind of nothing.
+1 for "never" - it's descriptive and readable. -Jon
+1 for "never"
Aug 10 2018
prev sibling parent Dukc <ajieskola gmail.com> writes:
On Saturday, 11 August 2018 at 05:01:50 UTC, docandrew wrote:
 On Thursday, 9 August 2018 at 15:50:02 UTC, w0rp wrote:
 A better name for this type is `never`, which is the name of 
 the TypeScript type with similar semantics. 
 https://www.typescriptlang.org/docs/handbook/basic-types.html#never `nothing`
is also a decent name, used in some other languages, but `never` makes it more
obvious that a function never returns, and isn't as easy to confuse with
`void`, which is a different kind of nothing.
+1 for "never" - it's descriptive and readable. -Jon
And brings us closer to Rust, which is a good thing. But it does not matter, since the PR isn't suggesting any name for it -the user can create any alias of it he/she wants. Personally, I think the most accurate term would be "Paradox" but again it does not matter for sake of this DIP.
Aug 11 2018
prev sibling parent Timon Gehr <timon.gehr gmx.ch> writes:
On 09.08.2018 05:02, Mike Parker wrote:
 This is the feedback thread for the first round of Community Review for 
 DIP 1017, "Add Bottom Type":
 
 https://github.com/dlang/DIPs/blob/8274b0f600075e4553b41c31f4b77be2d917
b40/DIPs/DIP1017.md 
 
 
 All review-related feedback on and discussion of the DIP should occur in 
 this thread. The review period will end at 11:59 PM ET on August 24, or 
 when I make a post declaring it complete.
 
 At the end of Round 1, if further review is deemed necessary, the DIP 
 will be scheduled for another round. Otherwise, it will be queued for 
 the Final Review and Formal Assessment by the language maintainers.
 
 Please familiarize yourself with the documentation for the Community 
 Review before participating.
 
 https://github.com/dlang/DIPs/blob/master/PROCEDURE.md#community-review
 
 Thanks in advance to all who participate.
Copy-paste of my comment on the DIP pull request: "`Tbottom* → Tbottom` and `Tbottom[] → Tbottom` seem a bit unprincipled. I'd have rather expected to see `Tbottom* == typeof(null)` and `Tbottom[] == typeof([])`. In general, I'd advise against having special rules with regards to type construction, as special behavior like this can harm generic code." I think if we in fact want to have some sort of "bottom propagation" nonetheless, it should be expression-based, not type-based.
Aug 09 2018