Skip to content

Commit a60d9b0

Browse files
Nigel-Ecmajskeet
authored andcommitted
This commit embeds the reworked §13.6.2 into the rest of the text by dealing with thge linkages between them.
In particular: - The term *declarator* has been turned into the defined term ***declarator*** thus allowing other clauses which used to refer to *local_variable_declarator* to use it instead and simplify language at the same time. - The wording of the scope of a `for` variable has been made consisent between Statements & Basic Concepts – just word smithing using a blending of the two, no change in semantics. - The production *local_variable_type* has been moved from `foreach` to the textually earlier declaration expression, just seems more logical. I'll now remove the "draft" status of the PR, go at it folks!
1 parent 0ccbed0 commit a60d9b0

File tree

5 files changed

+16
-16
lines changed

5 files changed

+16
-16
lines changed

standard/basic-concepts.md

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -599,7 +599,7 @@ The ***scope*** of a name is the region of program text within which it is possi
599599
- The scope of a label declared in a *labeled_statement* ([§13.5](statements.md#135-labeled-statements)) is the *block* in which the declaration occurs.
600600
- The scope of a local variable declared in a *local_variable_declaration* ([§13.6.2](statements.md#1362-local-variable-declarations)) is the *block* in which the declaration occurs.
601601
- The scope of a local variable declared in a *switch_block* of a `switch` statement ([§13.8.3](statements.md#1383-the-switch-statement)) is the *switch_block*.
602-
- The scope of a local variable declared in a *for_initializer* of a `for` statement ([§13.9.4](statements.md#1394-the-for-statement)) is the *for_initializer*, the *for_condition*, the *for_iterator*, and the contained *statement* of the `for` statement.
602+
- The scope of a local variable declared in a *for_initializer* of a `for` statement ([§13.9.4](statements.md#1394-the-for-statement)) is the *for_initializer*, *for_condition*, *for_iterator*, and *embedded_statement* of the `for` statement.
603603
- The scope of a local constant declared in a *local_constant_declaration* ([§13.6.3](statements.md#1363-local-constant-declarations)) is the *block* in which the declaration occurs. It is a compile-time error to refer to a local constant in a textual position that precedes its *constant_declarator*.
604604
- The scope of a variable declared as part of a *foreach_statement*, *using_statement*, *lock_statement* or *query_expression* is determined by the expansion of the given construct.
605605
@@ -624,7 +624,7 @@ Within the scope of a namespace, class, struct, or enumeration member it is poss
624624
>
625625
> *end example*
626626
627-
Within the scope of a local variable, it is a compile-time error to refer to the local variable in a textual position that precedes the *local_variable_declarator* of the local variable.
627+
Within the scope of a local variable, it is a compile-time error to refer to the local variable in a textual position that precedes its declarator.
628628
629629
> *Example*:
630630
>
@@ -653,7 +653,7 @@ Within the scope of a local variable, it is a compile-time error to refer to the
653653
> }
654654
> ```
655655
>
656-
> In the `Fmethod above, the first assignment to `i` specifically does not refer to the field declared in the outer scope. Rather, it refers to the local variable and it results in a compile-time error because it textually precedes the declaration of the variable. In the `Gmethod, the use of `j` in the initializer for the declaration of `j` is valid because the use does not precede the *local_variable_declarator*. In the `Hmethod, a subsequent *local_variable_declarator* correctly refers to a local variable declared in an earlier *local_variable_declarator* within the same *local_variable_declaration*.
656+
> In the `Fmethod above, the first assignment to `i` specifically does not refer to the field declared in the outer scope. Rather, it refers to the local variable and it results in a compile-time error because it textually precedes the declaration of the variable. In the `Gmethod, the use of `j` in the initializer for the declaration of `j` is valid because the use does not precede the declarator. In the `Hmethod, a subsequent declarator correctly refers to a local variable declared in an earlier declarator within the same *local_variable_declaration*.
657657
>
658658
> *end example*
659659
<!-- markdownlint-disable MD028 -->

standard/expressions.md

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3148,7 +3148,7 @@ stackalloc_element_initializer
31483148
<!-- The following restrictions apply to C# 7.3, they are relaxed in C# 8 -->
31493149
A *stackalloc_expression* is only permitted in two contexts:
31503150

3151-
1. The *expression*, `E`, of a *local_variable_initializer* of a *local_variable_declaration* ([§13.6.2](statements.md#1362-local-variable-declarations)); and
3151+
1. The initializing *expression*, `E`, of a *local_variable_declaration* ([§13.6.2](statements.md#1362-local-variable-declarations)); and
31523152
2. The right operand *expression*, `E`, of a simple assignment ([$12.21.2](expressions.md#12212-simple-assignment)) which itself occurs as a *expression_statement* ([§13.7](statements.md#137-expression-statements))
31533153

31543154
In both contexts the *stackalloc_expression* is only permitted to occur as:
@@ -4712,6 +4712,11 @@ A declaration expression declares a local variable.
47124712
declaration_expression
47134713
: local_variable_type identifier
47144714
;
4715+
4716+
local_variable_type
4717+
: type
4718+
| 'var'
4719+
;
47154720
```
47164721

47174722
The *simple_name* `_` is also considered a declaration expression if simple name lookup did not find an associated declaration ([§12.8.4](expressions.md#1284-simple-names)). When used as a declaration expression, `_` is called a *simple discard*. It is semantically equivalent to `var _`, but is permitted in more places.

standard/statements.md

Lines changed: 3 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -311,7 +311,7 @@ Implicitly typed declarations contain the contextual keyword ([§6.4.4](lexical-
311311
- If there is no type named `var` in scope and the input matches *implicitly_typed_local_variable_declaration* then it is chosen;
312312
- Otherwise if a type named `var` is in scope then *implicitly_typed_local_variable_declaration* is not considered as a possible match.
313313

314-
Within a *local_variable_declaration* each variable is introduced by a *declarator*, which is one of *implicitly_typed_local_variable_declarator*, *explicitly_typed_local_variable_declarator* or *ref_local_variable_declarator* for impicitly typed, explicitly typed and ref local variables respectively. The declarator defines the name (*identifier*) and initial value, if any, of the introduced variable.
314+
Within a *local_variable_declaration* each variable is introduced by a ***declarator***, which is one of *implicitly_typed_local_variable_declarator*, *explicitly_typed_local_variable_declarator* or *ref_local_variable_declarator* for impicitly typed, explicitly typed and ref local variables respectively. The declarator defines the name (*identifier*) and initial value, if any, of the introduced variable.
315315

316316
If there are multiple declarators in a declaration then they are processed, including any initializing expressions, in order left to right ([§9.4.4.5](variables.md#9445-declaration-statements)).
317317

@@ -343,7 +343,7 @@ The value of a local variable is obtained in an expression using a *simple_name*
343343
344344
The scope of a local variable introduced by a *local_variable_declaration* is defined as follows ([§7.7](basic-concepts.md#77-scopes)):
345345
346-
- If the declaration occurs as a *for_initializer* then the scope is the *local_variable_declaration* from the *declarator* for the variable to the end of the declaration, the *for_condition*, the *for_iterator*, and the *embedded_statement* ([§13.9.4](statements.md#1394-the-for-statement));
346+
- If the declaration occurs as a *for_initializer* then the scope is the *for_initializer*, *for_condition*, *for_iterator*, and *embedded_statement* ([§13.9.4](statements.md#1394-the-for-statement));
347347
- If the declaration occurs as a *resource_acquisition* then the scope is the outermost block of the semantically equivalent expansion of the *using_statement* ([§13.14](statements.md#1314-the-using-statement));
348348
- Otherwise the scope is the block in which the declaration occurs.
349349
@@ -1063,7 +1063,7 @@ statement_expression_list
10631063
;
10641064
```
10651065

1066-
The *for_initializer*, if present, consists of either a *local_variable_declaration* ([§13.6.2](statements.md#1362-local-variable-declarations)) or a list of *statement_expression*s ([§13.7](statements.md#137-expression-statements)) separated by commas. The scope of a local variable declared by a *for_initializer* starts at the *local_variable_declarator* for the variable and extends to the end of the embedded statement. The scope includes the *for_condition* and the *for_iterator*.
1066+
The *for_initializer*, if present, consists of either a *local_variable_declaration* ([§13.6.2](statements.md#1362-local-variable-declarations)) or a list of *statement_expression*s ([§13.7](statements.md#137-expression-statements)) separated by commas. The scope of a local variable declared by a *for_initializer* is the *for_initializer*, *for_condition*, *for_iterator*, and *embedded_statement*.
10671067

10681068
The *for_condition*, if present, shall be a *boolean_expression* ([§12.24](expressions.md#1224-boolean-expressions)).
10691069

@@ -1097,11 +1097,6 @@ foreach_statement
10971097
: 'foreach' '(' ref_kind? local_variable_type identifier 'in'
10981098
expression ')' embedded_statement
10991099
;
1100-
1101-
local_variable_type
1102-
: type
1103-
| 'var'
1104-
;
11051100
```
11061101

11071102
The *local_variable_type* and *identifier* of a foreach statement declare the ***iteration variable*** of the statement. If the `var` identifier is given as the *local_variable_type*, and no type named `var` is in scope, the iteration variable is said to be an ***implicitly typed iteration variable***, and its type is taken to be the element type of the `foreach` statement, as specified below.

standard/unsafe-code.md

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1049,7 +1049,7 @@ When the outermost containing struct variable of a fixed-size buffer member is a
10491049
10501050
See [§12.8.21](expressions.md#12821-stack-allocation) for general information about the operator `stackalloc`. Here, the ability of that operator to result in a pointer is discussed.
10511051
1052-
In an unsafe context if a *stackalloc_expression* ([§12.8.21](expressions.md#12821-stack-allocation)) occurs as the *local_variable_initializer* of a *local_variable_declaration* ([§13.6.2](statements.md#1362-local-variable-declarations)), where the *local_variable_type* is either a pointer type ([§23.3](unsafe-code.md#233-pointer-types)) or inferred (`var`), then the result of the *stackalloc_expression* is a pointer of type `T *` to be beginning of the allocated block, where `T` is the *unmanaged_type* of the *stackalloc_expression*.
1052+
In an unsafe context if a *stackalloc_expression* ([§12.8.21](expressions.md#12821-stack-allocation)) occurs as the initializing expression of a *local_variable_declaration* ([§13.6.2](statements.md#1362-local-variable-declarations)), where the *local_variable_type* is either a pointer type ([§23.3](unsafe-code.md#233-pointer-types)) or inferred (`var`), then the result of the *stackalloc_expression* is a pointer of type `T *` to be beginning of the allocated block, where `T` is the *unmanaged_type* of the *stackalloc_expression*.
10531053
10541054
In all other respects the semantics of *local_variable_declaration*s ([§13.6.2](statements.md#1362-local-variable-declarations)) and *stackalloc_expression*s ([§12.8.21](expressions.md#12821-stack-allocation)) in unsafe contexts follow those defined for safe contexts.
10551055

standard/variables.md

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -124,7 +124,7 @@ A ***local variable*** is declared by a *local_variable_declaration*, *declarati
124124
125125
A *local_variable_declaration* can occur in a *block*, a *for_statement*, a *switch_block*, or a *using_statement*. A *declaration_expression* can occur as an `out` *argument_value*, and as a *tuple_element* that is the target of a deconstructing assignment ([§12.21.2](expressions.md#12212-simple-assignment)).
126126
127-
The lifetime of a local variable is the portion of program execution during which storage is guaranteed to be reserved for it. This lifetime extends from entry into the scope with which it is associated, at least until execution of that scope ends in some way. (Entering an enclosed *block*, calling a method, or yielding a value from an iterator block suspends, but does not end, execution of the current scope.) If the local variable is captured by an anonymous function ([§12.19.6.2](expressions.md#121962-captured-outer-variables)), its lifetime extends at least until the delegate or expression tree created from the anonymous function, along with any other objects that come to reference the captured variable, are eligible for garbage collection. If the parent scope is entered recursively or iteratively, a new instance of the local variable is created each time, and its *local_variable_initializer*, if any, is evaluated each time.
127+
The lifetime of a local variable is the portion of program execution during which storage is guaranteed to be reserved for it. This lifetime extends from entry into the scope with which it is associated, at least until execution of that scope ends in some way. (Entering an enclosed *block*, calling a method, or yielding a value from an iterator block suspends, but does not end, execution of the current scope.) If the local variable is captured by an anonymous function ([§12.19.6.2](expressions.md#121962-captured-outer-variables)), its lifetime extends at least until the delegate or expression tree created from the anonymous function, along with any other objects that come to reference the captured variable, are eligible for garbage collection. If the parent scope is entered recursively or iteratively, a new instance of the local variable is created each time, and its initializer, if any, is evaluated each time.
128128
129129
> *Note*: A local variable is instantiated each time its scope is entered. This behavior is visible to user code containing anonymous methods. *end note*
130130
<!-- markdownlint-disable MD028 -->
@@ -142,7 +142,7 @@ The lifetime of a local variable is the portion of program execution during whic
142142
143143
A local variable introduced by a *local_variable_declaration* or *declaration_expression* is not automatically initialized and thus has no default value. Such a local variable is considered initially unassigned.
144144
145-
> *Note*: A *local_variable_declaration* that includes a *local_variable_initializer* is still initially unassigned. Execution of the declaration behaves exactly like an assignment to the variable ([§9.4.4.5](variables.md#9445-declaration-statements)). Using a variable before its *local_variable_initializer* has been executed; e.g., within the initializer expression itself or by using a *goto_statement* which bypasses the initializer; is a compile-time error:
145+
> *Note*: A *local_variable_declaration* that includes an initializer is still initially unassigned. Execution of the declaration behaves exactly like an assignment to the variable ([§9.4.4.5](variables.md#9445-declaration-statements)). Using a variable before its initializer has been executed; e.g., within the initializer expression itself or by using a *goto_statement* which bypasses the initializer; is a compile-time error:
146146
>
147147
> <!-- Example: {template:"code-in-main-without-using", name:"LocalVariables", expectedErrors:["CS0165"], expectedWarnings:["CS0162"]} -->
148148
> ```csharp
@@ -153,7 +153,7 @@ A local variable introduced by a *local_variable_declaration* or *declaration_ex
153153
> L: x += 1; // error: x not definitely assigned
154154
> ```
155155
>
156-
> Within the scope of a local variable, it is a compile-time error to refer to that local variable in a textual position that precedes its *local_variable_declarator*.
156+
> Within the scope of a local variable, it is a compile-time error to refer to that local variable in a textual position that precedes its declarator.
157157
>
158158
> *end note*
159159

0 commit comments

Comments
 (0)