Skip to content

Commit 9c359ee

Browse files
dkorpeldlang-bot
authored andcommitted
Document named arguments
Fix issue 24241
1 parent 6f82f13 commit 9c359ee

File tree

3 files changed

+89
-27
lines changed

3 files changed

+89
-27
lines changed

spec/expression.dd

Lines changed: 30 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -1621,7 +1621,7 @@ $(GNAME NamedArgument):
16211621
$(GLINK AssignExpression)
16221622
)
16231623

1624-
$(P A callable expression can precede a list of arguments in parentheses.)
1624+
$(P A callable expression can precede a list of named arguments in parentheses.)
16251625

16261626
---
16271627
void f(int, int);
@@ -1630,20 +1630,32 @@ f(5, 6);
16301630
(&f)(5, 6);
16311631
---
16321632

1633-
$(P A type can precede a list of arguments.)
1633+
$(H4 $(LNAME2 argument-parameter-matching, Matching Arguments to Parameters))
16341634

1635-
---
1636-
struct S
1637-
{
1638-
int x, y;
1639-
}
1640-
1641-
S s = S(1, 2);
1642-
---
1635+
$(P
1636+
Arguments in the `NamedArgumentList` are matched to function parameters as follows:
1637+
)
16431638

1644-
$(P See also: $(RELATIVE_LINK2 uniform_construction_syntax,
1645-
Uniform construction syntax for built-in scalar types))
1639+
$(P
1640+
If the first argument has no name, it will be assigned to the first function parameter.
1641+
)
1642+
$(P
1643+
A named argument is assigned to the function parameter with the same name.
1644+
It is an error if no such parameter exists.
1645+
)
1646+
$(P
1647+
Any other argument is assigned to the next parameter relative to the preceding argument's parameter.
1648+
It is an error if no such field exists, i.e. when the preceding argument assigns to the last parameter.
1649+
)
1650+
$(P
1651+
Assigning a parameter more than once is an error.
1652+
Not assigning a parameter any argument is also an error,
1653+
unless the parameter has a $(DDSUBLINK spec/function, function-default-args, Default Argument).
1654+
)
16461655

1656+
$(H4 $(LNAME2 type-constructor-arguments, Constructing a Type with an Argument List))
1657+
$(P A type can precede a list of arguments.
1658+
See: $(DDSUBLINK spec/struct, struct-literal, Struct Literals)) and $(RELATIVE_LINK2 uniform_construction_syntax, Uniform construction syntax for built-in scalar types))
16471659

16481660
$(H3 $(LEGACY_LNAME2 index_operations, index_expressions, Index Operations))
16491661

@@ -2499,6 +2511,12 @@ $(H3 $(LNAME2 uniform_construction_syntax, Uniform construction syntax for built
24992511
auto b = wchar(); // same as: wchar.init
25002512
---
25012513

2514+
$(P The argument may not be given a name:)
2515+
2516+
---
2517+
auto a = short(x: 1); // Error
2518+
---
2519+
25022520
$(P See also: $(DDSUBLINK spec/type, usual-arithmetic-conversions, Usual Arithmetic Conversions).)
25032521

25042522

spec/function.dd

Lines changed: 6 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1287,6 +1287,12 @@ $(H2 $(LNAME2 function-overloading, Function Overloading))
12871287
$(LI exact match)
12881288
)
12891289

1290+
$(P Named Arguments are resolved for a candidate according to
1291+
$(DDSUBLINK spec/expression, argument-parameter-matching, Matching Arguments to Parameters).
1292+
If this fails (for example, because the overload does not have a parameter with an argument's assigned named),
1293+
the level is $(I no match). Other than that, named arguments do not affect the matching level.
1294+
)
1295+
12901296
$(P Each argument (including any $(CODE this) reference) is
12911297
compared against the function's corresponding parameter to
12921298
determine the match level for that argument. The match level
@@ -1694,10 +1700,6 @@ pure void f()
16941700
}
16951701
---
16961702

1697-
$(P If the default value for a parameter is given, all following
1698-
parameters must also have default values.
1699-
)
1700-
17011703
$(P See also: function type aliases
17021704
$(DDSUBLINK spec/declaration, alias-function, with default values).)
17031705

spec/struct.dd

Lines changed: 53 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -464,7 +464,7 @@ void test(int i)
464464
$(H2 $(LEGACY_LNAME2 StructLiteral, struct-literal, Struct Literals))
465465

466466
$(P A struct literal consists of the name of the struct followed
467-
by a parenthesized argument list:)
467+
by a parenthesized named argument list:)
468468

469469
$(SPEC_RUNNABLE_EXAMPLE_RUN
470470
---
@@ -473,31 +473,58 @@ $(H2 $(LEGACY_LNAME2 StructLiteral, struct-literal, Struct Literals))
473473
int foo(S s) { return s.x; }
474474

475475
foo( S(1, 2) ); // set field x to 1, field y to 2
476+
foo( S(y: 2, x: 1) ); // same as above
476477
---
477478
)
478479

479480
$(P Struct literals are syntactically like function calls.
480-
If a struct has a member function named $(CODE opCall), then
481+
If a struct has a $(RELATIVE_LINK2 struct-constructor, Constructor)
482+
or a member function named `opCall`, then
481483
struct literals for that struct are not possible. See also
482484
$(DDSUBLINK spec/operatoroverloading, FunctionCall, opCall operator overloading)
483485
for the issue workaround.)
484486
$(P
485-
It is an error if there are more arguments than fields of
486-
the struct.
487-
If there are fewer arguments than fields, the remaining
488-
fields are initialized with their respective default
489-
initializers.)
487+
If the first argument has no name, it will be assigned to the struct field that is defined first lexically.
488+
)
489+
$(P
490+
A named argument is assigned to the struct field with the same name.
491+
It is an error if no such field exists.
492+
)
493+
$(P
494+
Any other argument is assigned to the next lexically defined struct field relative to the preceding argument's struct field.
495+
It is an error if no such field exists, i.e. when the preceding argument assigns to the last struct field.
496+
)
497+
$(P
498+
It is also an error to assign a field more than once.
499+
)
490500
$(P
491-
If there is a union field in the struct, only the first
501+
Any fields not assigned a value are initialized with their respective default initializers.
502+
)
503+
$(NOTE
504+
These rules are consistent with function calls, see $(DDSUBLINK spec/function, argument-parameter-matching, Matching Arguments to Parameters).
505+
)
506+
$(P
507+
If there is a union field in the struct, only one
492508
member of the union can be initialized inside a
493509
struct literal. This matches the behaviour for union literals.
494510
)
495511

512+
$(SPEC_RUNNABLE_EXAMPLE_FAIL
513+
---
514+
struct S { int x = 1; int y = 2, int z = 3; }
515+
516+
S s0 = S(y: 5, 6, x: 4); // `6` is assigned to field `z`, which comes after `y`
517+
S s1 = S(y: 5, z: 6); // Field x is not assigned, set to default initializer `1`
518+
S s2 = S(y: 5, x: 4, 5); // Error: field `y` is assigned twice
519+
S s3 = S(z: 2, 3); // Error: no field beyond `z`
520+
---
521+
)
522+
496523
$(H2 $(LNAME2 union-literal, Union Literals))
497524

498-
$(P A union literal is like a struct literal, but only the first field can
499-
be initialized with an initializer expression. Any field larger than the
500-
first will have the remainder of its memory initialized to zero.
525+
$(P A union literal is like a struct literal, but only one field can
526+
be initialized with an initializer expression.
527+
The remainder of the union's memory is initialized to zero.
501528
)
502529

503530
$(SPEC_RUNNABLE_EXAMPLE_RUN
@@ -657,6 +684,21 @@ $(H2 $(LEGACY_LNAME2 Struct-Constructor, struct-constructor, Struct Constructors
657684
---
658685
)
659686

687+
$(P Named arguments will be forwarded to the constructor and match parameter names, not struct field names.)
688+
689+
$(SPEC_RUNNABLE_EXAMPLE_FAIL
690+
---
691+
struct S
692+
{
693+
int x;
694+
int y;
695+
this(int y, int z) { this.x = y; this.y = z; }
696+
}
697+
S a = S(x: 3, y: 4); // Error: constructor has no parameter named `x`
698+
S b = S(y: 3, 4); // `y: 3` will set field `x` through parameter `y`
699+
---
700+
)
701+
660702
$(P A $(I default constructor) (i.e. one with an empty $(GLINK2 function, ParameterList))
661703
is not allowed.)
662704

0 commit comments

Comments
 (0)