DIP 1020--Named Parameters--Community Review Round 2

Paul Backus snarwin at gmail.com
Tue Sep 10 17:30:23 UTC 2019


On Tuesday, 10 September 2019 at 09:06:23 UTC, Mike Parker wrote:
> This is the feedback thread for the second round of Community 
> Review for DIP 1020, "Named Parameters":
>
> https://github.com/dlang/DIPs/blob/c723d8f4e3ac2d5bcaf8cdff87e1507f09669ca6/DIPs/DIP1020.md

Summary of review: in general, this DIP should do a better job of 
explaining the reasoning behind its choices of syntax and 
semantics, especially in cases where clear alternatives were 
available. Pros and cons should be explicitly discussed, ideally 
with examples to illustrate them.

Detailed comments follow.

> Prior Work
>
> Dyalect

Why does the DIP include some random programmer's personal hobby 
language alongside ones with significant adoption like C# and 
Swift? Is it just to give an example of C#'s syntax with a 
different reordering rule? If so, isn't the fact that you 
couldn't find a mainstream example of this reordering rule 
evidence against considering it?

> Python
>
> [...]
> Parameter syntax: ** Identifier

This is inaccurate, or at least incomplete. All function 
parameters in Python can be passed by name; no special parameter 
syntax is required to enable named arguments. The syntax `** 
Identifier` (usually written `**kwargs`) is used specifically for 
*variadic* keyword arguments.

> Parameters must be marked as accepting named arguments, 
> otherwise there will
> be no way to determine which overload to resolve.

The DIP needs to explain why this is true, not just assert it. At 
the very least, it should give an example of a function call for 
which overload resolution would fail if named parameters were not 
explicitly marked.

> It is the author's opinion that the is expression is heavily 
> overloaded and
> doing too much. It should be possible to access the names of 
> named template
> parameters outside of an instantiated template, but it should 
> be done with a
> mechanism other than the is expression.

Personal opinion is an extremely weak justification, and unlikely 
to convince anyone who does not already agree with the DIP's 
author. This section would be much more convincing if it compared 
and contrasted both approaches, and listed the pros and cons of 
each.

> The @named attribute prevents clashes with other existing 
> language features
> like template specializations (e.g., T:V or T=int). It aims to 
> be opt-in
> rather than opt-out to prevent clashes with core semantics of 
> the D
> programming language like function overloading.

The DIP should give specific examples of these "clashes" and 
explain how @named prevents them, rather than speaking in vague, 
general terms.

> The order of evaluation of named function arguments follows the 
> lexical order
> of the argument list (full, not subset).

What does "(full, not subset)" mean? This is the only usage of 
the word "subset" in the entire DIP. The DIP should define any 
new terms it intends to use, rather than assume that the reader 
will infer the correct meaning from context.

> Two new traits are added to support type inspection. The first 
> addition is
> the isNamedParameter trait, which allows a given parameter from 
> the parameter
> list of a function, delegate, or a function pointer to be 
> inspected for the
> presence of the @named attribute. This is intended to be used 
> with the
> __parameters specialization of the is expression. The second 
> addition is the
> getNamedParameters trait, which returns a list of all named 
> parameters from
> the parameter list of a given template, function, delegate, or 
> function
> pointer.

Why not have isNamedParameter work for templates too, and get rid 
of getNamedParameters?

> Overload resolution for symbols (for function and template 
> declarations) is
> performed without taking named parameters into account. 
> Ignoring named
> parameters in both cases means that the relevant algorithms and 
> user code
> does not need to change to accommodate named parameters but 
> they must be
> modified to filter them out. This is in line with the current 
> behavior. A
> side effect of this is that name mangling does not need to 
> change to
> accommodate these new parameters.
>
> [...]
>
>     void foo(int a) {
>     }
>
>     void foo(int a, @named int b) {
>     }
>
> [...]
>
>     foo(1); // error: matches both declarations
>     foo(1, b: 2); // error: matches both declarations

Given that the function calls are unambiguous as written, it 
seems very strange for the compiler to reject them. The DIP 
should explain, preferably with examples, what problems would be 
caused by allowing the compiler to accept these calls--i.e., what 
"algorithms and user code" would need to be changed, and how 
burdensome those changes would be.

> Template declarations that have named parameters expose the 
> named parameter as a member of the template.

This feature is not essential to the DIP, so its inclusion needs 
to be justified separately.

> Manifest constant templates and templated aliases are treated 
> as if they were
> eponymous templates and do expose named parameters as members.

Non-eponymous members of eponymous templates are currently 
inaccessible from outside the template body, so this will require 
changes to D's name lookup rules. Example:

    template size(T_)
    {
        alias T = T_;
        enum size = T_.sizeof;
    }

    // Error: no property T for type ulong
    pragma(msg, size!int.T);

> * named arguments at the end of an argument list may appear in 
> any order
>
> * named arguments may be interleaved with positional arguments 
> out of
> sequence, but if there are more than one they must match the 
> order in which
> the named parameters are declared

The DIP should explain why these particular reordering rules were 
chosen instead of any of the alternatives from previous 
proposals, or from the examples given in the "Prior Work" section.


More information about the Digitalmars-d mailing list