Skip to content

Commit e47c2d6

Browse files
authored
Spec ref safety for with() elements (#9859)
1 parent 4a8c204 commit e47c2d6

File tree

1 file changed

+31
-0
lines changed

1 file changed

+31
-0
lines changed

proposals/collection-expression-arguments.md

Lines changed: 31 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -324,6 +324,37 @@ int[] a = [with(), 1, 2, 3]; // error: arguments not supported
324324
int[] b = [with(length: 1), 3]; // error: arguments not supported
325325
```
326326

327+
## Ref safety
328+
329+
We adjust the [collection-expressions.md#ref-safety](https://github.com/dotnet/csharplang/blob/main/proposals/csharp-12.0/collection-expressions.md#ref-safety) rules to account for the `with()` element.
330+
331+
See also16.4.15 Safe context constraint](https://github.com/dotnet/csharpstandard/blob/draft-v7/standard/structs.md#16415-safe-context-constraint).
332+
333+
### Create methods
334+
335+
This section applies to collection-expressions whose target type meets the constraints defined in [CollectionBuilderAttribute methods](#collectionbuilderattribute-methods).
336+
337+
The *safe-context* is determined by modifying a clause from [collection-expressions.md#ref-safety](https://github.com/dotnet/csharplang/blob/main/proposals/csharp-12.0/collection-expressions.md#ref-safety) (changes in **bold**):
338+
339+
> * If the target type is a *ref struct type* with a [*create method*](#create-methods), the safe-context of the collection expression is the [*safe-context of an invocation*](https://github.com/dotnet/csharpstandard/blob/draft-v7/standard/structs.md#164126-method-and-property-invocation) of the create method where **the arguments are the `with()` element arguments followed by the collection expression as the argument for the last parameter (the `ReadOnlySpan<E>` parameter).**
340+
341+
The [*method arguments must match*](https://github.com/dotnet/csharplang/blob/main/proposals/csharp-11.0/low-level-struct-improvements.md#method-arguments-must-match) constraint applies to the collection expression. Similarly to the *safe-context* determination above, the *method arguments must match* constraint is applied by treating the collection expression as an invocation of the create method, where the arguments are the `with()` element arguments followed by the collection expression as the argument for the last parameter.
342+
343+
### Constructor calls
344+
345+
This section applies to collection-expressions whose target type meets the constraints defined in [Constructors](#constructors).
346+
347+
For a collection-expression of a *ref struct type* of the following form:
348+
`[with(a₁, a₂, ..., aₙ), e₁, e₂, ..., eₙ]`
349+
350+
The *safe-context* of the collection expression is the narrowest of the *safe-contexts* of the following expressions:
351+
- An object creation expression `new C(a₁, a₂, ..., aₙ)`, where `C` is the target type
352+
- The element expressions `e₁, e₂, ..., eₙ` (either the expressions themselves, or the spread value in the case of a spread element).
353+
354+
The [*method arguments must match*](https://github.com/dotnet/csharplang/blob/main/proposals/csharp-11.0/low-level-struct-improvements.md#method-arguments-must-match) constraint applies to the collection expression. The constraint is applied by treating the collection expression as an object creation of the form `new C(a₁, a₂, ..., aₙ) { e₁, e₂, ..., eₙ }` per [low-level-struct-improvements.md#rules-for-object-initializers](https://github.com/dotnet/csharplang/blob/main/proposals/csharp-11.0/low-level-struct-improvements.md#rules-for-object-initializers).
355+
- Expression elements are treated as if they are collection element initializers.
356+
- Spread elements are treated similarly, by temporarily assuming that `C` has an `Add(SpreadType spread)` method, where `SpreadType` is the type of the spread value.
357+
327358
## Answered questions
328359

329360
### `dynamic` arguments

0 commit comments

Comments
 (0)