Skip to content

Commit 53b4bb0

Browse files
committed
Updating array literals with spread elements
1 parent d8eca59 commit 53b4bb0

5 files changed

+60
-18
lines changed
Binary file not shown.
Binary file not shown.
1.75 KB
Binary file not shown.
9.97 KB
Binary file not shown.

doc/spec.md

+60-18
Original file line numberDiff line numberDiff line change
@@ -426,7 +426,7 @@ getX({ x: 0, y: 0, color: "red" }); // Extra fields Ok
426426
getX({ x: 0 }); // Error: supplied parameter does not match
427427
```
428428

429-
See section [0](#0) for more information about type comparisons.
429+
See section [3.10](#3.10) for more information about type comparisons.
430430

431431
## <a name="1.5"/>1.5 Contextual Typing
432432

@@ -961,7 +961,7 @@ The Number primitive type corresponds to the similarly named JavaScript primitiv
961961

962962
The `number` keyword references the Number primitive type and numeric literals may be used to write values of the Number primitive type.
963963

964-
For purposes of determining type relationships (section [0](#0)) and accessing properties (section [4.10](#4.10)), the Number primitive type behaves as an object type with the same properties as the global interface type 'Number'.
964+
For purposes of determining type relationships (section [3.10](#3.10)) and accessing properties (section [4.10](#4.10)), the Number primitive type behaves as an object type with the same properties as the global interface type 'Number'.
965965

966966
Some examples:
967967

@@ -978,7 +978,7 @@ The Boolean primitive type corresponds to the similarly named JavaScript primiti
978978

979979
The `boolean` keyword references the Boolean primitive type and the `true` and `false` literals reference the two Boolean truth values.
980980

981-
For purposes of determining type relationships (section [0](#0)) and accessing properties (section [4.10](#4.10)), the Boolean primitive type behaves as an object type with the same properties as the global interface type 'Boolean'.
981+
For purposes of determining type relationships (section [3.10](#3.10)) and accessing properties (section [4.10](#4.10)), the Boolean primitive type behaves as an object type with the same properties as the global interface type 'Boolean'.
982982

983983
Some examples:
984984

@@ -994,7 +994,7 @@ The String primitive type corresponds to the similarly named JavaScript primitiv
994994

995995
The `string` keyword references the String primitive type and string literals may be used to write values of the String primitive type.
996996

997-
For purposes of determining type relationships (section [0](#0)) and accessing properties (section [4.10](#4.10)), the String primitive type behaves as an object type with the same properties as the global interface type 'String'.
997+
For purposes of determining type relationships (section [3.10](#3.10)) and accessing properties (section [4.10](#4.10)), the String primitive type behaves as an object type with the same properties as the global interface type 'String'.
998998

999999
Some examples:
10001000

@@ -1098,6 +1098,8 @@ Array literals (section [4.6](#4.6)) may be used to create values of array types
10981098
var a: string[] = ["hello", "world"];
10991099
```
11001100

1101+
A type is said to be an ***array-like type*** if it is assignable (section [3.10.4](#3.10.4)) to the type `any[]`.
1102+
11011103
### <a name="3.3.3"/>3.3.3 Tuple Types
11021104

11031105
***Tuple types*** represent JavaScript arrays with individually tracked element types. Tuple types are written using tuple type literals (section [3.7.5](#3.7.5)). A tuple type combines a set of numerically named properties with the members of an array type. Specifically, a tuple type
@@ -1137,6 +1139,8 @@ interface KeyValuePair<K, V> extends Array<K | V> { 0: K; 1: V; }
11371139
var x: KeyValuePair<number, string> = [10, "ten"];
11381140
```
11391141

1142+
A type is said to be a ***tuple-like type*** if it has a property with the numeric name '0'.
1143+
11401144
### <a name="3.3.4"/>3.3.4 Function Types
11411145

11421146
An object type containing one or more call signatures is said to be a ***function type***. Function types may be written using function type literals (section [3.7.7](#3.7.7)) or by including call signatures in object type literals.
@@ -1156,7 +1160,7 @@ Every object type is composed from zero or more of the following kinds of member
11561160

11571161
Properties are either ***public***, ***private***, or ***protected*** and are either ***required*** or ***optional***:
11581162

1159-
* Properties in a class declaration may be designated public, private, or protected, while properties declared in other contexts are always considered public. Private members are only accessible within their declaring class, as described in section [8.2.2](#8.2.2), and private properties match only themselves in subtype and assignment compatibility checks, as described in section [0](#0). Protected members are only accessible within their declaring class and classes derived from it, as described in section [8.2.2](#8.2.2), and protected properties match only themselves and overrides in subtype and assignment compatibility checks, as described in section [0](#0).
1163+
* Properties in a class declaration may be designated public, private, or protected, while properties declared in other contexts are always considered public. Private members are only accessible within their declaring class, as described in section [8.2.2](#8.2.2), and private properties match only themselves in subtype and assignment compatibility checks, as described in section [3.10](#3.10). Protected members are only accessible within their declaring class and classes derived from it, as described in section [8.2.2](#8.2.2), and protected properties match only themselves and overrides in subtype and assignment compatibility checks, as described in section [3.10](#3.10).
11601164
* Properties in an object type literal or interface declaration may be designated required or optional, while properties declared in other contexts are always considered required. Properties that are optional in the target type of an assignment may be omitted from source objects, as described in section [3.10.4](#3.10.4).
11611165

11621166
Call and construct signatures may be ***specialized*** (section [3.8.2.4](#3.8.2.4)) by including parameters with string literal types. Specialized signatures are used to express patterns where specific string values for some parameters cause the types of other parameters or the function result to become further specialized.
@@ -1282,7 +1286,7 @@ interface G<T, U extends Function> {
12821286

12831287
the base constraint of 'T' is the empty object type, and the base constraint of 'U' and 'V' is 'Function'.
12841288

1285-
For purposes of determining type relationships (section [0](#0)), type parameters appear to be subtypes of their base constraint. Likewise, in property accesses (section [4.10](#4.10)), `new` operations (section [4.11](#4.11)), and function calls (section [4.12](#4.12)), type parameters appear to have the members of their base constraint, but no other members.
1289+
For purposes of determining type relationships (section [3.10](#3.10)), type parameters appear to be subtypes of their base constraint. Likewise, in property accesses (section [4.10](#4.10)), `new` operations (section [4.11](#4.11)), and function calls (section [4.12](#4.12)), type parameters appear to have the members of their base constraint, but no other members.
12861290

12871291
### <a name="3.5.2"/>3.5.2 Type Argument Lists
12881292

@@ -2280,6 +2284,17 @@ When an object literal is contextually typed by a type that includes a string in
22802284
22812285
## <a name="4.6"/>4.6 Array Literals
22822286
2287+
Array literals are extended to support the spread (`...`) operator.
2288+
2289+
&emsp;&emsp;*ElementList:* *( Modified )*
2290+
&emsp;&emsp;&emsp;*Elision<sub>opt</sub>*&emsp;*AssignmentExpression*
2291+
&emsp;&emsp;&emsp;*Elision<sub>opt</sub>*&emsp;*SpreadElement*
2292+
&emsp;&emsp;&emsp;*ElementList*&emsp;`,`&emsp;*Elision<sub>opt</sub>*&emsp;*AssignmentExpression*
2293+
&emsp;&emsp;&emsp;*ElementList*&emsp;`,`&emsp;*Elision<sub>opt</sub>*&emsp;*SpreadElement*
2294+
2295+
&emsp;&emsp;*SpreadElement:*
2296+
&emsp;&emsp;&emsp;`...`&emsp;*AssignmentExpression*
2297+
22832298
An array literal
22842299
22852300
```TypeScript
@@ -2290,24 +2305,41 @@ denotes a value of an array type (section [3.3.2](#3.3.2)) or a tuple type (sect
22902305
22912306
Each element expression in a non-empty array literal is processed as follows:
22922307
2293-
* If the array literal is contextually typed (section [4.19](#4.19)) by a type *T* and *T* has a property with the numeric name *N*, where *N* is the index of the element expression in the array literal, the element expression is contextually typed by the type of that property.
2308+
* If the array literal contains no spread elements, and if the array literal is contextually typed (section [4.19](#4.19)) by a type *T* and *T* has a property with the numeric name *N*, where *N* is the index of the element expression in the array literal, the element expression is contextually typed by the type of that property.
22942309
* Otherwise, if the array literal is contextually typed by a type *T* with a numeric index signature, the element expression is contextually typed by the type of the numeric index signature.
22952310
* Otherwise, the element expression is not contextually typed.
22962311
22972312
The resulting type an array literal expression is determined as follows:
22982313
22992314
* If the array literal is empty, the resulting type is an array type with the element type Undefined.
2300-
* Otherwise, if the array literal is contextually typed by a type that has a property with the numeric name '0', the resulting type is a tuple type constructed from the types of the element expressions.
2301-
* Otherwise, the resulting type is an array type with an element type that is the union of the types of the element expressions.
2315+
* Otherwise, if the array literal contains no spread elements and is contextually typed by a tuple-like type (section [3.3.3](#3.3.3)), the resulting type is a tuple type constructed from the types of the element expressions.
2316+
* Otherwise, if the array literal contains no spread elements and is an array assignment pattern in a destructuring assignment (section [4.17.1](#4.17.1)), the resulting type is a tuple type constructed from the types of the element expressions.
2317+
* Otherwise, the resulting type is an array type with an element type that is the union of the types of the non-spread element expressions and the numeric index signature types of the spread element expressions.
2318+
2319+
A spread element must specify an expression of an array-like type (section [3.3.2](#3.3.2)), or otherwise an error occurs.
23022320
2303-
The rules above mean that an array literal is always of an array type, unless it is contextually typed by a type with numerically named properties (such as a tuple type). For example
2321+
The rules above mean that an array literal is always of an array type, unless it is contextually typed by a tuple-like type. For example
23042322
23052323
```TypeScript
23062324
var a = [1, 2]; // number[]
23072325
var b = ["hello", true]; // (string | boolean)[]
23082326
var c: [number, string] = [3, "three"]; // [number, string]
23092327
```
23102328
2329+
When the output target is ECMAScript 3 or 5, array literals containing spread elements are rewritten to invocations of the `concat` method. For example, the assignments
2330+
2331+
```TypeScript
2332+
var a = [2, 3, 4];
2333+
var b = [0, 1, ...a, 5, 6];
2334+
```
2335+
2336+
are rewritten to
2337+
2338+
```TypeScript
2339+
var a = [2, 3, 4];
2340+
var b = [0, 1].concat(a, [5, 6]);
2341+
```
2342+
23112343
## <a name="4.7"/>4.7 Parentheses
23122344
23132345
A parenthesized expression
@@ -2970,10 +3002,10 @@ In a destructuring assignment expression, the type of the expression on the righ
29703002
* *S* has an apparent property with the property name specified in *P* of a type that is assignable to the target given in *P*, or
29713003
* *P* specifies a numeric property name and *S* has a numeric index signature of a type that is assignable to the target given in *P*, or
29723004
* *S* has a string index signature of a type that is assignable to the target given in *P*.
2973-
* *V* is an array assignment pattern, *S* is the type Any, an array type, or a tuple type, and, for each assignment element *E* in *V*,
3005+
* *V* is an array assignment pattern, *S* is the type Any or an array-like type (section [3.3.2](#3.3.2)), and, for each assignment element *E* in *V*,
29743006
* *S* is the type Any, or
2975-
* *S* is a tuple type with a property named *N* of a type that is assignable to the target given in *E*, where *N* is the numeric index of *E* in the array assignment pattern, or
2976-
* the numeric index signature type of *S* is assignable to the target given in *E*.
3007+
* *S* is a tuple-like type (section [3.3.3](#3.3.3)) with a property named *N* of a type that is assignable to the target given in *E*, where *N* is the numeric index of *E* in the array assignment pattern, or
3008+
* *S* is not a tuple-like type and the numeric index signature type of *S* is assignable to the target given in *E*.
29773009
29783010
In an assignment property or element that includes a default value, the type of the default value must be assignable to the target given in the assignment property or element.
29793011
@@ -3017,9 +3049,10 @@ Type checking of an expression is improved in several contexts by factoring in t
30173049
* the type of the property with a matching name in the contextual type, if any, or otherwise
30183050
* for a numerically named property, the numeric index type of the contextual type, if any, or otherwise
30193051
* the string index type of the contextual type, if any.
3020-
* In a contextually typed array literal expression, an element expression at index *N* is contextually typed by
3052+
* In a contextually typed array literal expression containing no spread elements, an element expression at index *N* is contextually typed by
30213053
* the type of the property with the numeric name *N* in the contextual type, if any, or otherwise
30223054
* the numeric index type of the contextual type, if any.
3055+
* In a contextually typed array literal expression containing one or more spread elements, an element expression at index *N* is contextually typed by the numeric index type of the contextual type, if any.
30233056
* In a contextually typed parenthesized expression, the contained expression is contextually typed by the same type.
30243057
* In a type assertion, the expression is contextually typed by the indicated type.
30253058
* In a || operator expression, if the expression is contextually typed, the operands are contextually typed by the same type. Otherwise, the right expression is contextually typed by the type of the left expression.
@@ -3303,9 +3336,9 @@ The type *T* associated with a binding element is determined as follows:
33033336
* If *S* is the Any type:
33043337
* If the binding element specifies an initializer expression, *T* is the type of that initializer expression.
33053338
* Otherwise, *T* is the Any type.
3306-
* If S is not an array type (i.e. assignable to the type `any[]`), no type is associated with the binding property and an error occurs.
3339+
* If *S* is not an array-like type (section [3.3.2](#3.3.2)), no type is associated with the binding property and an error occurs.
33073340
* If the binding element is a rest element, *T* is an array type with an element type *E*, where *E* is the type of the numeric index signature of *S*.
3308-
* Otherwise, if *S* is a tuple type:
3341+
* Otherwise, if *S* is a tuple-like type (section [3.3.3](#3.3.3)):
33093342
* Let *N* be the zero-based index of the binding element in the array binding pattern.
33103343
* If *S* has a property with the numerical name *N*, *T* is the type of that property.
33113344
* Otherwise, no type is associated with the binding element and an error occurs.
@@ -3368,7 +3401,7 @@ var _a = getSomeObject(),
33683401
z = _d === void 0 ? 10 : _d;
33693402
```
33703403
3371-
### <a name="5.1.3"/>5.1.3 Implied Type
3404+
### <a name="5.1.3"/>5.1.3 Implied Type
33723405
33733406
A variable, parameter, binding property, or binding element declaration that specifies a binding pattern has an ***implied type*** which is determined as follows:
33743407
@@ -3858,7 +3891,7 @@ class Location {
38583891
}
38593892
```
38603893
3861-
In the above example, 'SelectableControl' contains all of the members of 'Control', including the private 'state' property. Since 'state' is a private member it is only possible for descendants of 'Control' to implement 'SelectableControl'. This is because only descendants of 'Control' will have a 'state' private member that originates in the same declaration, which is a requirement for private members to be compatible (section [0](#0)).
3894+
In the above example, 'SelectableControl' contains all of the members of 'Control', including the private 'state' property. Since 'state' is a private member it is only possible for descendants of 'Control' to implement 'SelectableControl'. This is because only descendants of 'Control' will have a 'state' private member that originates in the same declaration, which is a requirement for private members to be compatible (section [3.10](#3.10)).
38623895
38633896
Within the 'Control' class it is possible to access the 'state' private member through an instance of 'SelectableControl'. Effectively, a 'SelectableControl' acts like a 'Control' that is known to have a 'select' method. The 'Button' and 'TextBox' classes are subtypes of 'SelectableControl' (because they both inherit from 'Control' and have a 'select' method), but the 'Image' and 'Location' classes are not.
38643897
@@ -5721,6 +5754,15 @@ This appendix contains a summary of the grammar found in the main document. As d
57215754
&emsp;&emsp;*SetAccessor:*
57225755
&emsp;&emsp;&emsp;`set`&emsp;*PropertyName*&emsp;`(`&emsp;*Identifier*&emsp;*TypeAnnotation<sub>opt</sub>*&emsp;`)`&emsp;`{`&emsp;*FunctionBody*&emsp;`}`
57235756
5757+
&emsp;&emsp;*ElementList:* *( Modified )*
5758+
&emsp;&emsp;&emsp;*Elision<sub>opt</sub>*&emsp;*AssignmentExpression*
5759+
&emsp;&emsp;&emsp;*Elision<sub>opt</sub>*&emsp;*SpreadElement*
5760+
&emsp;&emsp;&emsp;*ElementList*&emsp;`,`&emsp;*Elision<sub>opt</sub>*&emsp;*AssignmentExpression*
5761+
&emsp;&emsp;&emsp;*ElementList*&emsp;`,`&emsp;*Elision<sub>opt</sub>*&emsp;*SpreadElement*
5762+
5763+
&emsp;&emsp;*SpreadElement:*
5764+
&emsp;&emsp;&emsp;`...`&emsp;*AssignmentExpression*
5765+
57245766
&emsp;&emsp;*CallExpression:* *( Modified )*
57255767
&emsp;&emsp;&emsp;…
57265768
&emsp;&emsp;&emsp;`super`&emsp;`(`&emsp;*ArgumentList<sub>opt</sub>*&emsp;`)`

0 commit comments

Comments
 (0)