Hi folks,
To recap the discussion above, a few comments:
Move init vs decorator
The @destructor style of decorator is found to be confusing when applied to the moveinit case. To confirm Nick’s comment, if moveinit turned into init then per this proposal, it would be written as:
struct Thing:
var x: Int
@destructor
fn __init__(out self, *, move: Self):
self.x = move.x^
There are ways to address this with different tradeoffs - eg
-
add the ability for decorators to apply to arguments and have a
@destroysdecorator or somesuch (not very appealing for complexity reasons), -
define the move constructor as a
move()method which would take self and yield a new value. Not appealing because it loses “init” syntax and therefore loses the ability to fieldwise initialize self. -
teach people that
outarguments are not arguments even though they appear in the argument list syntactically (the current default per the proposal).
As many folks have said, these aren’t perfect by any stretch of the imagination. Move constructors are pretty rare to write though - Mojo synthesizes trivial ones, and Rust doesn’t even permit you to write them - so perhaps this is an acceptable weakness of the proposal.
Statement form
I still don’t agree that the statement form adds anything important here. I hear the arguments from proponents for this, but it makes the default and important cases more verbose and more difficult to explain (e.g. the move init and other cases) and - again - Mojo doesn’t depend on the position of this statement, so giving it an imperative form just illuminates confusion about the programming model, it doesn’t dispell it.
ASAP destruction is a thing, and a good thing.
Arg convention form
The major argument against argument convention is that it is confusing because it … isn’t an argument convention. I hear that argument, but against the other tradeoffs of other approaches, it seems like the “least bad” approach at least for now. It is simple, explainable, compact and uniform.
Path forward
The default is to keep what we have: deinit in the argument convention position. If and when we consider resyntaxing the copyinit/moveinit syntax (not a priority as far as I know, the team is focused on landing bigger ticket features) then we can come back to evaluating the tradeoffs and repaint this. Until then, I don’t see an approach that is significantly better-enough to be worth investing in.
-Chris