8. Types

A value is an entity that takes on one of nine types. There are nine types (Undefined, Null, Boolean, String, Number, Object, Reference, List, and Completion). Values of type Reference, List, and Completion are used only as intermediate results of expression evaluation and cannot be stored as properties of objects.

8.1 The Undefined Type

The Undefined type has exactly one value, called undefined. Any variable that has not been assigned a value has the value undefined.

8.2 The Null Type

The Null type has exactly one value, called null.

8.3 The Boolean Type

The Boolean type represents a logical entity having two values, called true and false.

8.4 The String Type

The String type is the set of all finite ordered sequences of zero or more 16-bit unsigned integer values ("elements"). The String type is generally used to represent textual data in a running ECMAScript program, in which case each element in the string is treated as a code point value (see section 6). Each element is regarded as occupying a position within the sequence. These positions are indexed with nonnegative integers. The first element (if any) is at position 0, the next element (if any) at position 1, and so on. The length of a string is the number of elements (i. e., 16-bit values) within it. The empty string has length zero and therefore contains no elements.

When a string contains actual textual data, each element is considered to be a single UTF-16 unit. Whether or not this is the actual storage format of a String, the characters within a String are numbered as though they were represented using UTF-16. All operations on Strings (except as otherwise stated) treat them as sequences of undifferentiated 16-bit unsigned integers; they do not ensure the resulting string is in normalised form, nor do they ensure language-sensitive results.

NOTE
The rationale behind these decisions was to keep the implementation of Strings as simple and high-performing as possible. The intent is that textual data coming into the execution environment from outside (e. g., user input, text read from a file or received over the network, etc.) be converted to Unicode Normalised Form C before the running program sees it. Usually this would occur at the same time incoming text is converted from its original character encoding to Unicode (and would impose no additional overhead). Since it is recommended that ECMAScript source code be in Normalised Form C, string literals are guaranteed to be normalised (if source text is guaranteed to be normalised), as long as they do not contain any Unicode escape sequences
.

8.5 The Number Type

The Number type has exactly 18437736874454810627 (that is, 264-253 +3) values, representing the double-precision 64-bit format IEEE 754 values as specified in the IEEE Standard for Binary Floating-Point Arithmetic, except that the 9007199254740990 (that is, 253-2) distinct "Not-a-Number" values of the IEEE Standard are represented in ECMAScript as a single special NaN value. (Note that the NaN value is produced by the program expression NaN, assuming that the globally defined variable NaN has not been altered by program execution.) In some implementations, external code might be able to detect a difference between various Non-a-Number values, but such behaviour is implementation-dependent; to ECMAScript code, all NaN values are indistinguishable from each other.

There are two other special values, called positive Infinity and negative Infinity. For brevity, these values are also referred to for expository purposes by the symbols +∞ and -∞, respectively. (Note that these two infinite number values are produced by the program expressions +Infinity (or simply Infinity) and -Infinity, assuming that the globally defined variable Infinity has not been altered by program execution.)

The other 18437736874454810624 (that is, 264-253 ) values are called the finite numbers. Half of these are positive numbers and half are negative numbers; for every finite positive number there is a corresponding negative number having the same magnitude.

Note that there is both a positive zero and a negative zero. For brevity, these values are also referred to for expository purposes by the symbols +0 and -0, respectively. (Note that these two zero number values are produced by the program expressions +0 (or simply 0) and -0.)

The 18437736874454810622 (that is, 264-253-2) finite nonzero values are of two kinds:

18428729675200069632 (that is, 264-254 ) of them are normalised, having the form

s * m * 2e

where s is +1 or -1, m is a positive integer less than 253 but not less than 252 , and e is an integer ranging from -1074 to 971, inclusive.

The remaining 9007199254740990 (that is, 253-2) values are denormalised, having the form

s * m * 2e

where s is +1 or -1, m is a positive integer less than 252, and e is -1074.

Note that all the positive and negative integers whose magnitude is no greater than 253 are representable in the Number type (indeed, the integer 0 has two representations, +0 and -0).

A finite number has an odd significand if it is nonzero and the integer m used to express it (in one of the two forms shown above) is odd. Otherwise, it has an even significand.

In this specification, the phrase "the number value for x" where x represents an exact nonzero real mathematical quantity (which might even be an irrational number such as π) means a number value chosen in the following manner. Consider the set of all finite values of the Number type, with -0 removed and with two additional values added to it that are not representable in the Number type, namely 21024 (which is +1 * 253 * 2971 )and -21024 (which is -1 * 253 * 2971 ). Choose the member of this set that is closest in value to x. If two values of the set are equally close, then the one with an even significand is chosen; for this purpose, the two extra values 21024 and -21024 are considered to have even significands. Finally, if 21024 was chosen, replace it with +∞; if -21024 was chosen, replace it with -∞; if +0 was chosen, replace it with -0 if and only if x is less than zero; any other chosen value is used unchanged. The result is the number value for x. (This procedure corresponds exactly to the behaviour of the IEEE 754 "round to nearest" mode.)

Some ECMAScript operators deal only with integers in the range -231 through 231-1, inclusive, or in the range 0 through 232-1, inclusive. These operators accept any value of the Number type but first convert each such value to one of 232 integer values. See the descriptions of the ToInt32 and ToUint32 operators in sections 0 and 0, respectively.

8.6 The Object Type

An Object is an unordered collection of properties. Each property consists of a name, a value and a set of attributes.

8.6.1 Property Attributes

A property can have zero or more attributes from the following set:

Attribute Description
ReadOnly The property is a read-only property. Attempts by ECMAScript code to write to the property will be ignored. (Note, however, that in some cases the value of a property with the ReadOnly attribute may change over time because of actions taken by the host environment; therefore "ReadOnly" does not mean "constant and unchanging"!)
DontEnum The property is not to be enumerated by a for-in enumeration (section 12.6.4).
DontDelete Attempts to delete the property will be ignored. See the description of the delete operator in section 11.4.1.
Internal Internal properties have no name and are not directly accessible via the property accessor operators. How these properties are accessed is implementation specific. How and when some of these properties are used is specified by the language specification.
8.6.2 Internal Properties and Methods

Internal properties and methods are not part of the language. They are defined by this specification purely for expository purposes. An implementation of ECMAScript must behave as if it produced and operated upon internal properties in the manner described here. For the purposes of this document, the names of internal properties are enclosed in double square brackets [[ ]]. When an algorithm uses an internal property of an object and the object does not implement the indicated internal property, a TypeError exception is thrown.

There are two types of access for normal (non-internal) properties: get and put, corresponding to retrieval and assignment, respectively.

Native ECMAScript objects have an internal property called [[Prototype]]. The value of this property is either null or an object and is used for implementing inheritance. Properties of the [[Prototype]] object are visible as properties of the child object for the purposes of get access, but not for put access.

The following table summarises the internal properties used by this specification. The description indicates their behaviour for native ECMAScript objects. Host objects may implement these internal methods with any implementation-dependent behaviour, or it may be that a host object implements only some internal methods and not others.

Property Parameters Description
[[Prototype]] none The prototype of this object.
[[Class]] none A string value indicating the kind of this object.
[[Value]] none Internal state information associated with this object.
[[Get]] (PropertyName) Returns the value of the property.
[[Put]] (PropertyName, Value) Sets the specified property to Value.
[[CanPut]] (PropertyName) Returns a boolean value indicating whether a [[Put]] operation with PropertyName will succeed.
[[HasProperty]] (PropertyName) Returns a boolean value indicating whether the object already has a member with the given name.
[[Delete]] (PropertyName) Removes the specified property from the object.
[[DefaultValue]] (Hint) Returns a default value for the object, which should be a primitive value (not an object or reference).
[[Construct]] a list of argument values provided by the caller Constructs an object. Invoked via the new operator. Objects that implement this internal method are called constructors.
[[Call]] a list of argument values provided by the caller Executes code associated with the object. Invoked via a function call expression. Objects that implement this internal method are called functions.
[[HasInstance]] (Value) Returns a boolean value indicating whether Value delegates behaviour to this object. Of the native ECMAScript objects, only Function objects implement [[HasInstance]].
[[Scope]] none A scope chain that defines the environment in which a Function object is executed.
[[Match]] (String, Index) Tests for a regular expression match and returns a MatchResult value (see section 15.10.2.1).

Every object (including host objects) must implement the [[Prototype]] and [[Class]] properties and the [[Get]], [[Put]], [[CanPut]], [[HasProperty]], [[Delete]], and [[DefaultValue]] methods. (Note, however, that the [[DefaultValue]] method may, for some objects, simply throw a TypeError exception.)

The value of the [[Prototype]] property must be either an object or null, and every [[Prototype]] chain must have finite length (that is, starting from any object, recursively accessing the [[Prototype]] property must eventually lead to a null value). Whether or not a native object can have a host object as its [[Prototype]] depends on the implementation.

The value of the [[Class]] property is defined by this specification for every kind of built-in object. The value of the [[Class]] property of a host object may be any value, even a value used by a built-in object for its [[Class]] property. The value of a [[Class]] property is used internally to distinguish different kinds of built-in objects. Note that this specification does not provide any means for a program to access that value except through Object.prototype.toString (see 15.2.4.2).

For native objects the [[Get]], [[Put]], [[CanPut]], [[HasProperty]], [[Delete]] and [[DefaultValue]] methods behave as described in 8.6.2.1, 8.6.2.2, 8.6.2.3, 8.6.2.4, 8.6.2.5 and 8.6.2.6, respectively, except that Array objects have a slightly different implementation of the [[Put]] method (see 15.4.5.1). Host objects may implement these methods in any manner unless specified otherwise; for example, one possibility is that [[Get]] and [[Put]] for a particular host object indeed fetch and store property values but [[HasProperty]] always generates false.

In the following algorithm descriptions, assume O is a native ECMAScript object and P is a string.

8.6.2.1 [[Get]](P)

When the [[Get]] method of O is called with property name P, the following steps are taken:

1. If O doesn't have a property with name P, go to step 4.

2. Get the value of the property.

3. Return Result(2).

4. If the [[Prototype]] of O is null, return undefined.

5. Call the [[Get]] method of [[Prototype]] with property name P.

6. Return Result(5).

8.6.2.2 [[Put]](P, V)

When the [[Put]] method of O is called with property P and value V, the following steps are taken:

1. Call the [[CanPut]] method of O with name P.

2. If Result(1) is false, return.

3. If O doesn't have a property with name P, go to step 6.

4. Set the value of the property to V. The attributes of the property are not changed.

5. Return.

6. Create a property with name P, set its value to V and give it empty attributes.

7. Return.

Note, however, that if O is an Array object, it has a more elaborate [[Put]] method (15.4.5.1).

8.6.2.3 [[CanPut]](P)

The [[CanPut]] method is used only by the [[Put]] method.

When the [[CanPut]] method of O is called with property P, the following steps are taken:

1. If O doesn't have a property with name P, go to step 4.

2. If the property has the ReadOnly attribute, return false.

3. Return true.

4. If the [[Prototype]] of O is null, return true.

5. Call the [[CanPut]] method of [[Prototype]] of O with property name P.

6. Return Result(5).

8.6.2.4 [[HasProperty]](P)

When the [[HasProperty]] method of O is called with property name P, the following steps are taken:

1. If O has a property with name P, return true.

2. If the [[Prototype]] of O is null, return false.

3. Call the [[HasProperty]] method of [[Prototype]] with property name P.

4. Return Result(3).

8.6.2.5 [[Delete]](P)

When the [[Delete]] method of O is called with property name P, the following steps are taken:

1. If O doesn't have a property with name P, return true.

2. If the property has the DontDelete attribute, return false.

3. Remove the property with name P from O.

4. Return true.

8.6.2.6 [[DefaultValue]](hint)

When the [[DefaultValue]] method of O is called with hint String, the following steps are taken:

1. Call the [[Get]] method of object O with argument "toString".

2. If Result(1) is not an object, go to step 5.

3. Call the [[Call]] method of Result(1), with O as the this value and an empty argument list.

4. If Result(3) is a primitive value, return Result(3).

5. Call the [[Get]] method of object O with argument "valueOf".

6. If Result(5) is not an object, go to step 9.

7. Call the [[Call]] method of Result(5), with O as the this value and an empty argument list.

8. If Result(7) is a primitive value, return Result(7).

9. Throw a TypeError exception.

When the [[DefaultValue]] method of O is called with hint Number, the following steps are taken:

1. Call the [[Get]] method of object O with argument "valueOf".

2. If Result(1) is not an object, go to step 5.

3. Call the [[Call]] method of Result(1), with O as the this value and an empty argument list.

4. If Result(3) is a primitive value, return Result(3).

5. Call the [[Get]] method of object O with argument "toString".

6. If Result(5) is not an object, go to step 9.

7. Call the [[Call]] method of Result(5), with O as the this value and an empty argument list.

8. If Result(7) is a primitive value, return Result(7).

9. Throw a TypeError exception.

When the [[DefaultValue]] method of O is called with no hint, then it behaves as if the hint were Number, unless O is a Date object (see 15.9), in which case it behaves as if the hint were String.

The above specification of [[DefaultValue]] for native objects can return only primitive values. If a host object implements its own [[DefaultValue]] method, it must ensure that its [[DefaultValue]] method can return only primitive values.

8.7 The Reference Type

The internal Reference type is not a language data type. It is defined by this specification purely for expository purposes. An implementation of ECMAScript must behave as if it produced and operated upon references in the manner described here. However, a value of type Reference is used only as an intermediate result of expression evaluation and cannot be stored as the value of a variable or property.

The Reference type is used to explain the behaviour of such operators as delete, typeof, and the assignment operators. For example, the left-hand operand of an assignment is expected to produce a reference. The behaviour of assignment could, instead, be explained entirely in terms of a case analysis on the syntactic form of the left-hand operand of an assignment operator, but for one difficulty: function calls are permitted to return references. This possibility is admitted purely for the sake of host objects. No built-in ECMAScript function defined by this specification returns a reference and there is no provision for a user-defined function to return a reference. (Another reason not to use a syntactic case analysis is that it would be lengthy and awkward, affecting many parts of the specification.)

Another use of the Reference type is to explain the determination of the this value for a function call.

A Reference is a reference to a property of an object. A Reference consists of two components, the base object and the property name.

The following abstract operations are used in this specification to access the components of references:

The following abstract operations are used in this specification to operate on references:

8.7.1 GetValue(V)

1. If Type(V) is not Reference, return V.

2. Call GetBase(V).

3. If Result(2) is null, throw a ReferenceError exception.

4. Call the [[Get]] method of Result(2), passing GetPropertyName( V) for the property name.

5. Return Result(4).

8.7.2 PutValue(V, W)

1. If Type(V) is not Reference, throw a ReferenceError exception.

2. Call GetBase(V).

3. If Result(2) is null, go to step 6.

4. Call the [[Put]] method of Result(2), passing GetPropertyName(V) for the property name and W for the value.

5. Return.

6. Call the [[Put]] method for the global object, passing GetPropertyName(V) for the property name and W for the value.

7. Return.

8.8 The List Type

The internal List type is not a language data type. It is defined by this specification purely for expository purposes. An implementation of ECMAScript must behave as if it produced and operated upon List values in the manner described here. However, a value of the List type is used only as an intermediate result of expression evaluation and cannot be stored as the value of a variable or property.

The List type is used to explain the evaluation of argument lists (see 11.2.4) in new expressions and in function calls. Values of the List type are simply ordered sequences of values. These sequences may be of any length.

8.9 The Completion Type

The internal Completion type is not a language data type. It is defined by this specification purely for expository purposes. An implementation of ECMAScript must behave as if it produced and operated upon Completion values in the manner described here. However, a value of the Completion type is used only as an intermediate result of statement evaluation and cannot be stored as the value of a variable or property.

The Completion type is used to explain the behaviour of statements (break, continue, return and throw) that perform nonlocal transfers of control. Values of the Completion type are triples of the form (type, value, target), where type is one of normal, break, continue, return, or throw, value is any ECMAScript value or empty, and target is any ECMAScript identifier or empty.

The term "abrupt completion" refers to any completion with a type other than normal.