DataView - JavaScript

DataView
========

The **`DataView`** view provides a low-level interface for reading and writing multiple number types in a binary `ArrayBuffer`, without having to care about the platform's endianness.

Description
-----------

### Endianness

Multi-byte number formats are represented in memory differently depending on machine architecture — see Endianness for an explanation. `DataView` accessors provide explicit control of how data is accessed, regardless of the executing computer's endianness.

```js
const littleEndian = (() => {
  const buffer = new ArrayBuffer(2);
  new DataView(buffer).setInt16(0, 256, true /\* littleEndian \*/);
  // Int16Array uses the platform's endianness.
  return new Int16Array(buffer)[0] === 256;
})();
console.log(littleEndian); // true or false
```

### 64-bit Integer Values

Some browsers don't have support for `DataView.prototype.setBigInt64()` and `DataView.prototype.setBigUint64()`. So to enable 64-bit operations in your code that will work across browsers, you could implement your own `getUint64()` function, to obtain values with precision up to `Number.MAX_SAFE_INTEGER` — which could suffice for certain cases.

```js
function getUint64(dataview, byteOffset, littleEndian) {
  // split 64-bit number into two 32-bit (4-byte) parts
  const left = dataview.getUint32(byteOffset, littleEndian);
  const right = dataview.getUint32(byteOffset + 4, littleEndian);

  // combine the two 32-bit values
  const combined = littleEndian
    ? left + 2 \*\* 32 \* right
    : 2 \*\* 32 \* left + right;

  if (!Number.isSafeInteger(combined))
    console.warn(combined, "exceeds MAX\_SAFE\_INTEGER. Precision may be lost");

  return combined;
}
```

Alternatively, if you need full 64-bit range, you can create a `BigInt`. Further, although native BigInts are much faster than user-land library equivalents, BigInts will always be much slower than 32-bit integers in JavaScript due to the nature of their variable size.

```js
const BigInt = window.BigInt,
  bigThirtyTwo = BigInt(32),
  bigZero = BigInt(0);
function getUint64BigInt(dataview, byteOffset, littleEndian) {
  // split 64-bit number into two 32-bit (4-byte) parts
  const left = BigInt(dataview.getUint32(byteOffset | 0, !!littleEndian) >>> 0);
  const right = BigInt(
    dataview.getUint32(((byteOffset | 0) + 4) | 0, !!littleEndian) >>> 0,
  );

  // combine the two 32-bit values and return
  return littleEndian
    ? (right << bigThirtyTwo) | left
    : (left << bigThirtyTwo) | right;
}
```

Constructor
-----------

`DataView()`

Creates a new `DataView` object.

Instance properties
-------------------

These properties are defined on `DataView.prototype` and shared by all `DataView` instances.

`DataView.prototype.buffer`

The `ArrayBuffer` referenced by this view. Fixed at construction time and thus **read only.**

`DataView.prototype.byteLength`

The length (in bytes) of this view. Fixed at construction time and thus **read only.**

`DataView.prototype.byteOffset`

The offset (in bytes) of this view from the start of its `ArrayBuffer`. Fixed at construction time and thus **read only.**

`DataView.prototype.constructor`

The constructor function that created the instance object. For `DataView` instances, the initial value is the `DataView` constructor.

`DataView.prototype[@@toStringTag]`

The initial value of the `@@toStringTag` property is the string `"DataView"`. This property is used in `Object.prototype.toString()`.

Instance methods
----------------

`DataView.prototype.getBigInt64()`

Reads 8 bytes starting at the specified byte offset of this `DataView` and interprets them as a 64-bit signed integer.

`DataView.prototype.getBigUint64()`

Reads 8 bytes starting at the specified byte offset of this `DataView` and interprets them as a 64-bit unsigned integer.

`DataView.prototype.getFloat32()`

Reads 4 bytes starting at the specified byte offset of this `DataView` and interprets them as a 32-bit floating point number.

`DataView.prototype.getFloat64()`

Reads 8 bytes starting at the specified byte offset of this `DataView` and interprets them as a 64-bit floating point number.

`DataView.prototype.getInt16()`

Reads 2 bytes starting at the specified byte offset of this `DataView` and interprets them as a 16-bit signed integer.

`DataView.prototype.getInt32()`

Reads 4 bytes starting at the specified byte offset of this `DataView` and interprets them as a 32-bit signed integer.

`DataView.prototype.getInt8()`

Reads 1 byte at the specified byte offset of this `DataView` and interprets it as an 8-bit signed integer.

`DataView.prototype.getUint16()`

Reads 2 bytes starting at the specified byte offset of this `DataView` and interprets them as a 16-bit unsigned integer.

`DataView.prototype.getUint32()`

Reads 4 bytes starting at the specified byte offset of this `DataView` and interprets them as a 32-bit unsigned integer.

`DataView.prototype.getUint8()`

Reads 1 byte at the specified byte offset of this `DataView` and interprets it as an 8-bit unsigned integer.

`DataView.prototype.setBigInt64()`

Takes a BigInt and stores it as a 64-bit signed integer in the 8 bytes starting at the specified byte offset of this `DataView`.

`DataView.prototype.setBigUint64()`

Takes a BigInt and stores it as a 64-bit unsigned integer in the 8 bytes starting at the specified byte offset of this `DataView`.

`DataView.prototype.setFloat32()`

Takes a number and stores it as a 32-bit float in the 4 bytes starting at the specified byte offset of this `DataView`.

`DataView.prototype.setFloat64()`

Takes a number and stores it as a 64-bit float in the 8 bytes starting at the specified byte offset of this `DataView`.

`DataView.prototype.setInt16()`

Takes a number and stores it as a 16-bit signed integer in the 2 bytes at the specified byte offset of this `DataView`.

`DataView.prototype.setInt32()`

Takes a number and stores it as a 32-bit signed integer in the 4 bytes at the specified byte offset of this `DataView`.

`DataView.prototype.setInt8()`

Takes a number and stores it as an 8-bit signed integer in the byte at the specified byte offset of this `DataView`.

`DataView.prototype.setUint16()`

Takes a number and stores it as a 16-bit unsigned integer in the 2 bytes at the specified byte offset of this `DataView`.

`DataView.prototype.setUint32()`

Takes a number and stores it as a 32-bit unsigned integer in the 4 bytes at the specified byte offset of this `DataView`.

`DataView.prototype.setUint8()`

Takes a number and stores it as an 8-bit unsigned integer in the byte at the specified byte offset of this `DataView`.

Examples
--------

### Using DataView

```js
const buffer = new ArrayBuffer(16);
const view = new DataView(buffer, 0);

view.setInt16(1, 42);
view.getInt16(1); // 42
```

Specifications
--------------

| Specification |
| --- |
| ECMAScript Language Specification # sec-dataview-objects |

Browser compatibility
---------------------

BCD tables only load in the browser with JavaScript enabled. Enable JavaScript to view data.

See also
--------

* Polyfill of `DataView` in `core-js`
* `ArrayBuffer`
* `SharedArrayBuffer`


Number - JavaScript

Number
======

**`Number`** values represent floating-point numbers like `37` or `-9.25`.

The `Number` constructor contains constants and methods for working with numbers. Values of other types can be converted to numbers using the `Number()` function.

Description
-----------

Numbers are most commonly expressed in literal forms like `255` or `3.14159`. The lexical grammar contains a more detailed reference.

```js
255; // two-hundred and fifty-five
255.0; // same number
255 === 255.0; // true
255 === 0xff; // true (hexadecimal notation)
255 === 0b11111111; // true (binary notation)
255 === 0.255e3; // true (decimal exponential notation)
```

A number literal like `37` in JavaScript code is a floating-point value, not an integer. There is no separate integer type in common everyday use. (JavaScript also has a `BigInt` type, but it's not designed to replace Number for everyday uses. `37` is still a number, not a BigInt.)

When used as a function, `Number(value)` converts a string or other value to the Number type. If the value can't be converted, it returns `NaN`.

```js
Number("123"); // returns the number 123
Number("123") === 123; // true

Number("unicorn"); // NaN
Number(undefined); // NaN
```

### Number encoding

The JavaScript `Number` type is a double-precision 64-bit binary format IEEE 754 value, like `double` in Java or C#. This means it can represent fractional values, but there are some limits to the stored number's magnitude and precision. Very briefly, an IEEE 754 double-precision number uses 64 bits to represent 3 parts:

* 1 bit for the *sign* (positive or negative)
* 11 bits for the *exponent* (-1022 to 1023)
* 52 bits for the *mantissa* (representing a number between 0 and 1)

The mantissa (also called *significand*) is the part of the number representing the actual value (significant digits). The exponent is the power of 2 that the mantissa should be multiplied by. Thinking about it as scientific notation:

Number
=
(

−
1

)
sign

⋅
(
1
+
mantissa
)
⋅

2
exponent

\text{Number} = ({-1})^{\text{sign}} \cdot (1 + \text{mantissa}) \cdot 2^{\text{exponent}}

The mantissa is stored with 52 bits, interpreted as digits after `1.…` in a binary fractional number. Therefore, the mantissa's precision is 2-52 (obtainable via `Number.EPSILON`), or about 15 to 17 decimal places; arithmetic above that level of precision is subject to rounding.

The largest value a number can hold is 21023 × (2 - 2-52) (with the exponent being 1023 and the mantissa being 0.1111… in base 2), which is obtainable via `Number.MAX_VALUE`. Values higher than that are replaced with the special number constant `Infinity`.

Integers can only be represented without loss of precision in the range -253 + 1 to 253 - 1, inclusive (obtainable via `Number.MIN_SAFE_INTEGER` and `Number.MAX_SAFE_INTEGER`), because the mantissa can only hold 53 bits (including the leading 1).

More details on this are described in the ECMAScript standard.

### Number coercion

Many built-in operations that expect numbers first coerce their arguments to numbers (which is largely why `Number` objects behave similarly to number primitives). The operation can be summarized as follows:

* Numbers are returned as-is.
* `undefined` turns into `NaN`.
* `null` turns into `0`.
* `true` turns into `1`; `false` turns into `0`.
* Strings are converted by parsing them as if they contain a number literal. Parsing failure results in `NaN`. There are some minor differences compared to an actual number literal:
    + Leading and trailing whitespace/line terminators are ignored.
    + A leading `0` digit does not cause the number to become an octal literal (or get rejected in strict mode).
    + `+` and `-` are allowed at the start of the string to indicate its sign. (In actual code, they "look like" part of the literal, but are actually separate unary operators.) However, the sign can only appear once, and must not be followed by whitespace.
    + `Infinity` and `-Infinity` are recognized as literals. In actual code, they are global variables.
    + Empty or whitespace-only strings are converted to `0`.
    + Numeric separators are not allowed.
* BigInts throw a `TypeError` to prevent unintended implicit coercion causing loss of precision.
* Symbols throw a `TypeError`.
* Objects are first converted to a primitive by calling their `[@@toPrimitive]()` (with `"number"` as hint), `valueOf()`, and `toString()` methods, in that order. The resulting primitive is then converted to a number.

There are two ways to achieve nearly the same effect in JavaScript.

* Unary plus: `+x` does exactly the number coercion steps explained above to convert `x`.
* The `Number()` function: `Number(x)` uses the same algorithm to convert `x`, except that BigInts don't throw a `TypeError`, but return their number value, with possible loss of precision.

`Number.parseFloat()` and `Number.parseInt()` are similar to `Number()` but only convert strings, and have slightly different parsing rules. For example, `parseInt()` doesn't recognize the decimal point, and `parseFloat()` doesn't recognize the `0x` prefix.

#### Integer conversion

Some operations expect integers, most notably those that work with array/string indices, date/time components, and number radixes. After performing the number coercion steps above, the result is truncated to an integer (by discarding the fractional part). If the number is ±Infinity, it's returned as-is. If the number is `NaN` or `-0`, it's returned as `0`. The result is therefore always an integer (which is not `-0`) or ±Infinity.

Notably, when converted to integers, both `undefined` and `null` become `0`, because `undefined` is converted to `NaN`, which also becomes `0`.

#### Fixed-width number conversion

JavaScript has some lower-level functions that deal with the binary encoding of integer numbers, most notably bitwise operators and `TypedArray` objects. Bitwise operators always convert the operands to 32-bit integers. In these cases, after converting the value to a number, the number is then normalized to the given width by first truncating the fractional part and then taking the lowest bits in the integer's two's complement encoding.

```js
new Int32Array([1.1, 1.9, -1.1, -1.9]); // Int32Array(4) [ 1, 1, -1, -1 ]

new Int8Array([257, -257]); // Int8Array(2) [ 1, -1 ]
// 257 = 0001 0000 0001
// = 0000 0001 (mod 2^8)
// = 1
// -257 = 1110 1111 1111
// = 1111 1111 (mod 2^8)
// = -1 (as signed integer)

new Uint8Array([257, -257]); // Uint8Array(2) [ 1, 255 ]
// -257 = 1110 1111 1111
// = 1111 1111 (mod 2^8)
// = 255 (as unsigned integer)
```

Constructor
-----------

`Number()`

Creates a new `Number` value.

When `Number` is called as a constructor (with `new`), it creates a `Number` object, which is **not** a primitive. For example, `typeof new Number(42) === "object"`, and `new Number(42) !== 42` (although `new Number(42) == 42`).

**Warning:** You should rarely find yourself using `Number` as a constructor.

Static properties
-----------------

`Number.EPSILON`

The smallest interval between two representable numbers.

`Number.MAX_SAFE_INTEGER`

The maximum safe integer in JavaScript (253 - 1).

`Number.MAX_VALUE`

The largest positive representable number.

`Number.MIN_SAFE_INTEGER`

The minimum safe integer in JavaScript (-(253 - 1)).

`Number.MIN_VALUE`

The smallest positive representable number—that is, the positive number closest to zero (without actually being zero).

`Number.NaN`

Special "**N**ot **a** **N**umber" value.

`Number.NEGATIVE_INFINITY`

Special value representing negative infinity. Returned on overflow.

`Number.POSITIVE_INFINITY`

Special value representing infinity. Returned on overflow.

Static methods
--------------

`Number.isFinite()`

Determine whether the passed value is a finite number.

`Number.isInteger()`

Determine whether the passed value is an integer.

`Number.isNaN()`

Determine whether the passed value is `NaN`.

`Number.isSafeInteger()`

Determine whether the passed value is a safe integer (number between -(253 - 1) and 253 - 1).

`Number.parseFloat()`

This is the same as the global `parseFloat()` function.

`Number.parseInt()`

This is the same as the global `parseInt()` function.

Instance properties
-------------------

These properties are defined on `Number.prototype` and shared by all `Number` instances.

`Number.prototype.constructor`

The constructor function that created the instance object. For `Number` instances, the initial value is the `Number` constructor.

Instance methods
----------------

`Number.prototype.toExponential()`

Returns a string representing the number in exponential notation.

`Number.prototype.toFixed()`

Returns a string representing the number in fixed-point notation.

`Number.prototype.toLocaleString()`

Returns a string with a language sensitive representation of this number. Overrides the `Object.prototype.toLocaleString()` method.

`Number.prototype.toPrecision()`

Returns a string representing the number to a specified precision in fixed-point or exponential notation.

`Number.prototype.toString()`

Returns a string representing the specified object in the specified *radix* ("base"). Overrides the `Object.prototype.toString()` method.

`Number.prototype.valueOf()`

Returns the primitive value of the specified object. Overrides the `Object.prototype.valueOf()` method.

Examples
--------

### Using the Number object to assign values to numeric variables

The following example uses the `Number` object's properties to assign values to several numeric variables:

```js
const biggestNum = Number.MAX\_VALUE;
const smallestNum = Number.MIN\_VALUE;
const infiniteNum = Number.POSITIVE\_INFINITY;
const negInfiniteNum = Number.NEGATIVE\_INFINITY;
const notANum = Number.NaN;
```

### Integer range for Number

The following example shows the minimum and maximum integer values that can be represented as `Number` object.

```js
const biggestInt = Number.MAX\_SAFE\_INTEGER; // (2\*\*53 - 1) => 9007199254740991
const smallestInt = Number.MIN\_SAFE\_INTEGER; // -(2\*\*53 - 1) => -9007199254740991
```

When parsing data that has been serialized to JSON, integer values falling outside of this range can be expected to become corrupted when JSON parser coerces them to `Number` type.

A possible workaround is to use `String` instead.

Larger numbers can be represented using the `BigInt` type.

### Using Number() to convert a Date object

The following example converts the `Date` object to a numerical value using `Number` as a function:

```js
const d = new Date("1995-12-17T03:24:00");
console.log(Number(d));
```

This logs `819199440000`.

### Convert numeric strings and null to numbers

```js
Number("123"); // 123
Number("123") === 123; // true
Number("12.3"); // 12.3
Number("12.00"); // 12
Number("123e-1"); // 12.3
Number(""); // 0
Number(null); // 0
Number("0x11"); // 17
Number("0b11"); // 3
Number("0o11"); // 9
Number("foo"); // NaN
Number("100a"); // NaN
Number("-Infinity"); // -Infinity
```

Specifications
--------------

| Specification |
| --- |
| ECMAScript Language Specification # sec-number-objects |

Browser compatibility
---------------------

BCD tables only load in the browser with JavaScript enabled. Enable JavaScript to view data.

See also
--------

* Polyfill of modern `Number` behavior (with support binary and octal literals) in `core-js`
* `NaN`
* Arithmetic operators
* `Math`
* `BigInt`


Uint8ClampedArray - JavaScript

Uint8ClampedArray
=================

The **`Uint8ClampedArray`** typed array represents an array of 8-bit unsigned integers clamped to 0–255. The contents are initialized to `0`. Once established, you can reference elements in the array using the object's methods, or using standard array index syntax (that is, using bracket notation).

`Uint8ClampedArray` is a subclass of the hidden `TypedArray` class.

Constructor
-----------

`Uint8ClampedArray()`

Creates a new `Uint8ClampedArray` object.

Static properties
-----------------

*Also inherits static properties from its parent `TypedArray`*.

`Uint8ClampedArray.BYTES_PER_ELEMENT`

Returns a number value of the element size. `1` in the case of `Uint8ClampedArray`.

Static methods
--------------

*Inherits static methods from its parent `TypedArray`*.

Instance properties
-------------------

*Also inherits instance properties from its parent `TypedArray`*.

These properties are defined on `Uint8ClampedArray.prototype` and shared by all `Uint8ClampedArray` instances.

`Uint8ClampedArray.prototype.BYTES_PER_ELEMENT`

Returns a number value of the element size. `1` in the case of a `Uint8ClampedArray`.

`Uint8ClampedArray.prototype.constructor`

The constructor function that created the instance object. For `Uint8ClampedArray` instances, the initial value is the `Uint8ClampedArray` constructor.

Instance methods
----------------

*Inherits instance methods from its parent `TypedArray`*.

Examples
--------

### Different ways to create a Uint8ClampedArray

```js
// From a length
const uint8c = new Uint8ClampedArray(2);
uint8c[0] = 42;
uint8c[1] = 1337;
console.log(uint8c[0]); // 42
console.log(uint8c[1]); // 255 (clamped)
console.log(uint8c.length); // 2
console.log(uint8c.BYTES\_PER\_ELEMENT); // 1

// From an array
const x = new Uint8ClampedArray([21, 31]);
console.log(x[1]); // 31

// From another TypedArray
const y = new Uint8ClampedArray(x);
console.log(y[0]); // 21

// From an ArrayBuffer
const buffer = new ArrayBuffer(8);
const z = new Uint8ClampedArray(buffer, 1, 4);
console.log(z.byteOffset); // 1

// From an iterable
const iterable = (function\* () {
  yield\* [1, 2, 3];
})();
const uint8cFromIterable = new Uint8ClampedArray(iterable);
console.log(uint8cFromIterable);
// Uint8ClampedArray [1, 2, 3]
```

Specifications
--------------

| Specification |
| --- |
| ECMAScript Language Specification # table-49 |

Browser compatibility
---------------------

BCD tables only load in the browser with JavaScript enabled. Enable JavaScript to view data.

See also
--------

* Polyfill of `Uint8ClampedArray` in `core-js`
* JavaScript typed arrays guide
* `TypedArray`
* `ArrayBuffer`
* `DataView`


Function - JavaScript

Function
========

The **`Function`** object provides methods for functions. In JavaScript, every function is actually a `Function` object.

Constructor
-----------

`Function()`

Creates a new `Function` object. Calling the constructor directly can create functions dynamically but suffers from security and similar (but far less significant) performance issues to `eval()`. However, unlike `eval()`, the `Function` constructor creates functions that execute in the global scope only.

Instance properties
-------------------

These properties are defined on `Function.prototype` and shared by all `Function` instances.

`Function.prototype.arguments`
Deprecated

Non-standard

Represents the arguments passed to this function. For strict, arrow, async, and generator functions, accessing the `arguments` property throws a `TypeError`. Use the `arguments` object inside function closures instead.

`Function.prototype.caller`
Deprecated

Non-standard

Represents the function that invoked this function. For strict, arrow, async, and generator functions, accessing the `caller` property throws a `TypeError`.

`Function.prototype.constructor`

The constructor function that created the instance object. For `Function` instances, the initial value is the `Function` constructor.

These properties are own properties of each `Function` instance.

`displayName`
Non-standard
 Optional

The display name of the function.

`length`

Specifies the number of arguments expected by the function.

`name`

The name of the function.

`prototype`

Used when the function is used as a constructor with the `new` operator. It will become the new object's prototype.

Instance methods
----------------

`Function.prototype.apply()`

Calls a function with a given `this` value and optional arguments provided as an array (or an array-like object).

`Function.prototype.bind()`

Creates a new function that, when called, has its `this` keyword set to a provided value, optionally with a given sequence of arguments preceding any provided when the new function is called.

`Function.prototype.call()`

Calls a function with a given `this` value and optional arguments.

`Function.prototype.toString()`

 Returns a string representing the source code of the function.
 Overrides the `Object.prototype.toString` method.

`Function.prototype[@@hasInstance]()`

Specifies the default procedure for determining if a constructor function recognizes an object as one of the constructor's instances. Called by the `instanceof` operator.

Examples
--------

### Difference between Function constructor and function declaration

Functions created with the `Function` constructor do not create closures to their creation contexts; they always are created in the global scope. When running them, they will only be able to access their own local variables and global ones, not the ones from the scope in which the `Function` constructor was created. This is different from using `eval()` with code for a function expression.

```js
// Create a global property with `var`
var x = 10;

function createFunction1() {
  const x = 20;
  return new Function("return x;"); // this `x` refers to global `x`
}

function createFunction2() {
  const x = 20;
  function f() {
    return x; // this `x` refers to the local `x` above
  }
  return f;
}

const f1 = createFunction1();
console.log(f1()); // 10
const f2 = createFunction2();
console.log(f2()); // 20
```

While this code works in web browsers, `f1()` will produce a `ReferenceError` in Node.js, as `x` will not be found. This is because the top-level scope in Node is not the global scope, and `x` will be local to the module.

Specifications
--------------

| Specification |
| --- |
| ECMAScript Language Specification # sec-function-objects |

Browser compatibility
---------------------

BCD tables only load in the browser with JavaScript enabled. Enable JavaScript to view data.

See also
--------

* `function`
* `function` expression
* `AsyncFunction`
* `AsyncGeneratorFunction`
* `GeneratorFunction`
* Functions


Reflect - JavaScript

Reflect
=======

The **`Reflect`** namespace object contains static methods for invoking interceptable JavaScript object internal methods. The methods are the same as those of proxy handlers.

Description
-----------

Unlike most global objects, `Reflect` is not a constructor. You cannot use it with the `new` operator or invoke the `Reflect` object as a function. All properties and methods of `Reflect` are static (just like the `Math` object).

The `Reflect` object provides a collection of static functions which have the same names as the proxy handler methods.

The major use case of `Reflect` is to provide default forwarding behavior in `Proxy` handler traps. A trap is used to intercept an operation on an object — it provides a custom implementation for an object internal method. The `Reflect` API is used to invoke the corresponding internal method. For example, the code below creates a proxy `p` with a `deleteProperty` trap that intercepts the `[[Delete]]` internal method. `Reflect.deleteProperty()` is used to invoke the default `[[Delete]]` behavior on `targetObject` directly. You can replace it with `delete`, but using `Reflect` saves you from having to remember the syntax that each internal method corresponds to.

```js
const p = new Proxy(
  {},
  {
    deleteProperty(targetObject, property) {
      // Custom functionality: log the deletion
      console.log("Deleting property:", property);

      // Execute the default introspection behavior
      return Reflect.deleteProperty(targetObject, property);
    },
  },
);
```

The `Reflect` methods also allow finer control of how the internal method is invoked. For example, `Reflect.construct()` is the only way to construct a target function with a specific `new.target` value. If you use the `new` operator to invoke a function, the `new.target` value is always the function itself. This has important effects with subclassing. For another example, `Reflect.get()` allows you to run a getter with a custom `this` value, while property accessors always use the current object as the `this` value.

Nearly every `Reflect` method's behavior can be done with some other syntax or method. Some of these methods have corresponding static methods of the same name on `Object`, although they do have some subtle differences. For the exact differences, see the description for each `Reflect` method.

Static properties
-----------------

`Reflect[@@toStringTag]`

The initial value of the `@@toStringTag` property is the string `"Reflect"`. This property is used in `Object.prototype.toString()`.

Static methods
--------------

`Reflect.apply()`

Calls a `target` function with arguments as specified by the `argumentsList` parameter. See also `Function.prototype.apply()`.

`Reflect.construct()`

The `new` operator as a function. Equivalent to calling `new target(...argumentsList)`. Also provides the option to specify a different prototype.

`Reflect.defineProperty()`

Similar to `Object.defineProperty()`. Returns a boolean that is `true` if the property was successfully defined.

`Reflect.deleteProperty()`

The `delete` operator as a function. Equivalent to calling `delete target[propertyKey]`.

`Reflect.get()`

Returns the value of the property. Works like getting a property from an object (`target[propertyKey]`) as a function.

`Reflect.getOwnPropertyDescriptor()`

Similar to `Object.getOwnPropertyDescriptor()`. Returns a property descriptor of the given property if it exists on the object, `undefined` otherwise.

`Reflect.getPrototypeOf()`

Same as `Object.getPrototypeOf()`.

`Reflect.has()`

Returns a boolean indicating whether the target has the property. Either as own or inherited. Works like the `in` operator as a function.

`Reflect.isExtensible()`

Same as `Object.isExtensible()`. Returns a boolean that is `true` if the target is extensible.

`Reflect.ownKeys()`

Returns an array of the target object's own (not inherited) property keys.

`Reflect.preventExtensions()`

Similar to `Object.preventExtensions()`. Returns a boolean that is `true` if the update was successful.

`Reflect.set()`

A function that assigns values to properties. Returns a boolean that is `true` if the update was successful.

`Reflect.setPrototypeOf()`

A function that sets the prototype of an object. Returns a boolean that is `true` if the update was successful.

Examples
--------

### Detecting whether an object contains certain properties

```js
const duck = {
  name: "Maurice",
  color: "white",
  greeting() {
    console.log(`Quaaaack! My name is ${this.name}`);
  },
};

Reflect.has(duck, "color");
// true
Reflect.has(duck, "haircut");
// false
```

### Returning the object's own keys

```js
Reflect.ownKeys(duck);
// [ "name", "color", "greeting" ]
```

### Adding a new property to the object

```js
Reflect.set(duck, "eyes", "black");
// returns "true" if successful
// "duck" now contains the property "eyes: 'black'"
```

Specifications
--------------

| Specification |
| --- |
| ECMAScript Language Specification # sec-reflect-object |

Browser compatibility
---------------------

BCD tables only load in the browser with JavaScript enabled. Enable JavaScript to view data.

See also
--------

* `Proxy`


Error - JavaScript

Error
=====

**`Error`** objects are thrown when runtime errors occur. The `Error` object can also be used as a base object for user-defined exceptions. See below for standard built-in error types.

Description
-----------

Runtime errors result in new `Error` objects being created and thrown.

`Error` is a serializable object, so it can be cloned with `structuredClone()` or copied between Workers using `postMessage()`.

### Error types

Besides the generic `Error` constructor, there are other core error constructors in JavaScript. For client-side exceptions, see Exception handling statements.

`EvalError`

Creates an instance representing an error that occurs regarding the global function `eval()`.

`RangeError`

Creates an instance representing an error that occurs when a numeric variable or parameter is outside its valid range.

`ReferenceError`

Creates an instance representing an error that occurs when de-referencing an invalid reference.

`SyntaxError`

Creates an instance representing a syntax error.

`TypeError`

Creates an instance representing an error that occurs when a variable or parameter is not of a valid type.

`URIError`

Creates an instance representing an error that occurs when `encodeURI()` or `decodeURI()` are passed invalid parameters.

`AggregateError`

Creates an instance representing several errors wrapped in a single error when multiple errors need to be reported by an operation, for example by `Promise.any()`.

`InternalError`
Non-standard

Creates an instance representing an error that occurs when an internal error in the JavaScript engine is thrown. E.g. "too much recursion".

Constructor
-----------

`Error()`

Creates a new `Error` object.

Static methods
--------------

`Error.captureStackTrace()`
Non-standard

A non-standard V8 function that creates the `stack` property on an Error instance.

`Error.stackTraceLimit`
Non-standard

A non-standard V8 numerical property that limits how many stack frames to include in an error stacktrace.

`Error.prepareStackTrace()`
Non-standard
 Optional

A non-standard V8 function that, if provided by usercode, is called by the V8 JavaScript engine for thrown exceptions, allowing the user to provide custom formatting for stacktraces.

Instance properties
-------------------

These properties are defined on `Error.prototype` and shared by all `Error` instances.

`Error.prototype.constructor`

The constructor function that created the instance object. For `Error` instances, the initial value is the `Error` constructor.

`Error.prototype.name`

Represents the name for the type of error. For `Error.prototype.name`, the initial value is `"Error"`. Subclasses like `TypeError` and `SyntaxError` provide their own `name` properties.

`Error.prototype.stack`
Non-standard

A non-standard property for a stack trace.

These properties are own properties of each `Error` instance.

`cause`

Error cause indicating the reason why the current error is thrown — usually another caught error. For user-created `Error` objects, this is the value provided as the `cause` property of the constructor's second argument.

`columnNumber`
Non-standard

A non-standard Mozilla property for the column number in the line that raised this error.

`fileName`
Non-standard

A non-standard Mozilla property for the path to the file that raised this error.

`lineNumber`
Non-standard

A non-standard Mozilla property for the line number in the file that raised this error.

`message`

Error message. For user-created `Error` objects, this is the string provided as the constructor's first argument.

Instance methods
----------------

`Error.prototype.toString()`

Returns a string representing the specified object. Overrides the `Object.prototype.toString()` method.

Examples
--------

### Throwing a generic error

 Usually you create an `Error` object with the intention of raising it using the `throw` keyword.
 You can handle the error using the `try...catch` construct:

```js
try {
  throw new Error("Whoops!");
} catch (e) {
  console.error(`${e.name}: ${e.message}`);
}
```

### Handling a specific error type

You can choose to handle only specific error types by testing the error type with the `instanceof` keyword:

```js
try {
  foo.bar();
} catch (e) {
  if (e instanceof EvalError) {
    console.error(`${e.name}: ${e.message}`);
  } else if (e instanceof RangeError) {
    console.error(`${e.name}: ${e.message}`);
  }
  // etc.
  else {
    // If none of our cases matched leave the Error unhandled
    throw e;
  }
}
```

### Differentiate between similar errors

Sometimes a block of code can fail for reasons that require different handling, but which throw very similar errors (i.e. with the same type and message).

 If you don't have control over the original errors that are thrown, one option is to catch them and throw new `Error` objects that have more specific messages.
 The original error should be passed to the new `Error` in the constructor's `options` parameter as its `cause` property. This ensures that the original error and stack trace are available to higher-level try/catch blocks.

The example below shows this for two methods that would otherwise fail with similar errors (`doFailSomeWay()` and `doFailAnotherWay()`):

```js
function doWork() {
  try {
    doFailSomeWay();
  } catch (err) {
    throw new Error("Failed in some way", { cause: err });
  }
  try {
    doFailAnotherWay();
  } catch (err) {
    throw new Error("Failed in another way", { cause: err });
  }
}

try {
  doWork();
} catch (err) {
  switch (err.message) {
    case "Failed in some way":
      handleFailSomeWay(err.cause);
      break;
    case "Failed in another way":
      handleFailAnotherWay(err.cause);
      break;
  }
}
```

**Note:** If you are making a library, you should prefer to use error cause to discriminate between different errors emitted — rather than asking your consumers to parse the error message. See the error cause page for an example.

Custom error types can also use the `cause` property, provided the subclasses' constructor passes the `options` parameter when calling `super()`. The `Error()` base class constructor will read `options.cause` and define the `cause` property on the new error instance.

```js
class MyError extends Error {
  constructor(message, options) {
    // Need to pass `options` as the second parameter to install the "cause" property.
    super(message, options);
  }
}

console.log(new MyError("test", { cause: new Error("cause") }).cause);
// Error: cause
```

### Custom error types

You might want to define your own error types deriving from `Error` to be able to `throw new MyError()` and use `instanceof MyError` to check the kind of error in the exception handler. This results in cleaner and more consistent error handling code.

See "What's a good way to extend Error in JavaScript?" on StackOverflow for an in-depth discussion.

**Warning:** Builtin subclassing cannot be reliably transpiled to pre-ES6 code, because there's no way to construct the base class with a particular `new.target` without `Reflect.construct()`. You need additional configuration or manually call `Object.setPrototypeOf(this, CustomError.prototype)` at the end of the constructor; otherwise, the constructed instance will not be a `CustomError` instance. See the TypeScript FAQ for more information.

**Note:** Some browsers include the `CustomError` constructor in the stack trace when using ES2015 classes.

```js
class CustomError extends Error {
  constructor(foo = "bar", ...params) {
    // Pass remaining arguments (including vendor specific ones) to parent constructor
    super(...params);

    // Maintains proper stack trace for where our error was thrown (only available on V8)
    if (Error.captureStackTrace) {
      Error.captureStackTrace(this, CustomError);
    }

    this.name = "CustomError";
    // Custom debugging information
    this.foo = foo;
    this.date = new Date();
  }
}

try {
  throw new CustomError("baz", "bazMessage");
} catch (e) {
  console.error(e.name); // CustomError
  console.error(e.foo); // baz
  console.error(e.message); // bazMessage
  console.error(e.stack); // stacktrace
}
```

Specifications
--------------

| Specification |
| --- |
| ECMAScript Language Specification # sec-error-objects |

Browser compatibility
---------------------

BCD tables only load in the browser with JavaScript enabled. Enable JavaScript to view data.

See also
--------

* Polyfill of `Error` with `cause` support in `core-js`
* `throw`
* `try...catch`
* Stack trace API in the V8 docs


isNaN() - JavaScript

isNaN()
=======

The **`isNaN()`** function determines whether a value is `NaN`, first converting the value to a number if necessary. Because coercion inside the `isNaN()` function can be surprising, you may prefer to use `Number.isNaN()`.

Try it
------

Syntax
------

```js
isNaN(value)
```

### Parameters

`value`

The value to be tested.

### Return value

`true` if the given value is `NaN` after being converted to a number; otherwise, `false`.

Description
-----------

`isNaN()` is a function property of the global object.

For number values, `isNaN()` tests if the number is the value `NaN`. When the argument to the `isNaN()` function is not of type Number, the value is first coerced to a number, and the resulting value is then compared against `NaN`.

This behavior of `isNaN()` for non-numeric arguments can be confusing! For example, an empty string is coerced to 0, while a boolean is coerced to 0 or 1; both values are intuitively "not numbers", but they don't evaluate to `NaN`, so `isNaN()` returns `false`. Therefore, `isNaN()` answers neither the question "is the input the floating point `NaN` value" nor the question "is the input not a number".

`Number.isNaN()` is a more reliable way to test whether a value is the number value `NaN` or not. Alternatively, the expression `x !== x` can be used, and neither of the solutions is subject to the false positives that make the global `isNaN()` unreliable. To test if a value is a number, use `typeof x === "number"`.

The `isNaN()` function answers the question "is the input functionally equivalent to `NaN` when used in a number context". If `isNaN(x)` returns `false`, you can use `x` in an arithmetic expression as if it's a valid number that's not `NaN`. If `isNaN(x)` returns `true`, `x` will get coerced to `NaN` and make most arithmetic expressions return `NaN` (because `NaN` propagates). You can use this, for example, to test whether an argument to a function is arithmetically processable (usable "like" a number), and handle values that are not number-like by throwing an error, providing a default value, etc. This way, you can have a function that makes use of the full versatility JavaScript provides by implicitly converting values depending on context.

**Note:** The `+` operator performs both number addition and string concatenation. Therefore, even if `isNaN()` returns `false` for both operands, the `+` operator may still return a string, because it's not used as an arithmetic operator. For example, `isNaN("1")` returns `false`, but `"1" + 1` returns `"11"`. To be sure that you are working with numbers, coerce the value to a number and use `Number.isNaN()` to test the result.

Examples
--------

Note how `isNaN()` returns `true` for values that are not the value `NaN` but are not numbers either:

```js
isNaN(NaN); // true
isNaN(undefined); // true
isNaN({}); // true

isNaN(true); // false
isNaN(null); // false
isNaN(37); // false

// Strings
isNaN("37"); // false: "37" is converted to the number 37 which is not NaN
isNaN("37.37"); // false: "37.37" is converted to the number 37.37 which is not NaN
isNaN("37,5"); // true
isNaN("123ABC"); // true: Number("123ABC") is NaN
isNaN(""); // false: the empty string is converted to 0 which is not NaN
isNaN(" "); // false: a string with spaces is converted to 0 which is not NaN

// Dates
isNaN(new Date()); // false; Date objects can be converted to a number (timestamp)
isNaN(new Date().toString()); // true; the string representation of a Date object cannot be parsed as a number

// Arrays
isNaN([]); // false; the primitive representation is "", which coverts to the number 0
isNaN([1]); // false; the primitive representation is "1"
isNaN([1, 2]); // true; the primitive representation is "1,2", which cannot be parsed as number
```

Specifications
--------------

| Specification |
| --- |
| ECMAScript Language Specification # sec-isnan-number |

Browser compatibility
---------------------

BCD tables only load in the browser with JavaScript enabled. Enable JavaScript to view data.

See also
--------

* `NaN`
* `Number.isNaN()`


Int32Array - JavaScript

Int32Array
==========

The **`Int32Array`** typed array represents an array of 32-bit signed integers in the platform byte order. If control over byte order is needed, use `DataView` instead. The contents are initialized to `0`. Once established, you can reference elements in the array using the object's methods, or using standard array index syntax (that is, using bracket notation).

`Int32Array` is a subclass of the hidden `TypedArray` class.

Constructor
-----------

`Int32Array()`

Creates a new `Int32Array` object.

Static properties
-----------------

*Also inherits static properties from its parent `TypedArray`*.

`Int32Array.BYTES_PER_ELEMENT`

Returns a number value of the element size. `4` in the case of `Int32Array`.

Static methods
--------------

*Inherits static methods from its parent `TypedArray`*.

Instance properties
-------------------

*Also inherits instance properties from its parent `TypedArray`*.

These properties are defined on `Int32Array.prototype` and shared by all `Int32Array` instances.

`Int32Array.prototype.BYTES_PER_ELEMENT`

Returns a number value of the element size. `4` in the case of a `Int32Array`.

`Int32Array.prototype.constructor`

The constructor function that created the instance object. For `Int32Array` instances, the initial value is the `Int32Array` constructor.

Instance methods
----------------

*Inherits instance methods from its parent `TypedArray`*.

Examples
--------

### Different ways to create an Int32Array

```js
// From a length
const int32 = new Int32Array(2);
int32[0] = 42;
console.log(int32[0]); // 42
console.log(int32.length); // 2
console.log(int32.BYTES\_PER\_ELEMENT); // 4

// From an array
const x = new Int32Array([21, 31]);
console.log(x[1]); // 31

// From another TypedArray
const y = new Int32Array(x);
console.log(y[0]); // 21

// From an ArrayBuffer
const buffer = new ArrayBuffer(32);
const z = new Int32Array(buffer, 4, 4);
console.log(z.byteOffset); // 4

// From an iterable
const iterable = (function\* () {
  yield\* [1, 2, 3];
})();
const int32FromIterable = new Int32Array(iterable);
console.log(int32FromIterable);
// Int32Array [1, 2, 3]
```

Specifications
--------------

| Specification |
| --- |
| ECMAScript Language Specification # table-49 |

Browser compatibility
---------------------

BCD tables only load in the browser with JavaScript enabled. Enable JavaScript to view data.

See also
--------

* Polyfill of `Int32Array` in `core-js`
* JavaScript typed arrays guide
* `TypedArray`
* `ArrayBuffer`
* `DataView`


FinalizationRegistry - JavaScript

FinalizationRegistry
====================

A **`FinalizationRegistry`** object lets you request a callback when a value is garbage-collected.

Description
-----------

`FinalizationRegistry` provides a way to request that a *cleanup callback* get called at some point when a value registered with the registry has been *reclaimed* (garbage-collected). (Cleanup callbacks are sometimes called *finalizers*.)

**Note:** Cleanup callbacks should not be used for essential program logic. See Notes on cleanup callbacks for details.

You create the registry passing in the callback:

```js
const registry = new FinalizationRegistry((heldValue) => {
  // …
});
```

Then you register any value you want a cleanup callback for by calling the `register` method, passing in the value and a *held value* for it:

```js
registry.register(target, "some value");
```

The registry does not keep a strong reference to the value, as that would defeat the purpose (if the registry held it strongly, the value would never be reclaimed). In JavaScript, objects and non-registered symbols are garbage collectable, so they can be registered in a `FinalizationRegistry` object as the target or the token.

If `target` is reclaimed, your cleanup callback may be called at some point with the *held value* you provided for it (`"some value"` in the above). The held value can be any value you like: a primitive or an object, even `undefined`. If the held value is an object, the registry keeps a *strong* reference to it (so it can pass it to your cleanup callback later).

If you might want to unregister a registered target value later, you pass a third value, which is the *unregistration token* you'll use later when calling the registry's `unregister` function to unregister the value. The registry only keeps a weak reference to the unregister token.

It's common to use the target value itself as the unregister token, which is just fine:

```js
registry.register(target, "some value", target);
// …

// some time later, if you don't care about `target` anymore, unregister it
registry.unregister(target);
```

It doesn't have to be the same value, though; it can be a different one:

```js
registry.register(target, "some value", token);
// …

// some time later
registry.unregister(token);
```

### Avoid where possible

Correct use of `FinalizationRegistry` takes careful thought, and it's best avoided if possible. It's also important to avoid relying on any specific behaviors not guaranteed by the specification. When, how, and whether garbage collection occurs is down to the implementation of any given JavaScript engine. Any behavior you observe in one engine may be different in another engine, in another version of the same engine, or even in a slightly different situation with the same version of the same engine. Garbage collection is a hard problem that JavaScript engine implementers are constantly refining and improving their solutions to.

Here are some specific points included by the authors in the proposal that introduced `FinalizationRegistry`:

>
> Garbage collectors are complicated. If an application or library depends on GC cleaning up a WeakRef or calling a finalizer [cleanup callback] in a timely, predictable manner, it's likely to be disappointed: the cleanup may happen much later than expected, or not at all. Sources of variability include:
>
>
> * One object might be garbage-collected much sooner than another object, even if they become unreachable at the same time, e.g., due to generational collection.
> * Garbage collection work can be split up over time using incremental and concurrent techniques.
> * Various runtime heuristics can be used to balance memory usage, responsiveness.
> * The JavaScript engine may hold references to things which look like they are unreachable (e.g., in closures, or inline caches).
> * Different JavaScript engines may do these things differently, or the same engine may change its algorithms across versions.
> * Complex factors may lead to objects being held alive for unexpected amounts of time, such as use with certain APIs.
>
>
>

### Notes on cleanup callbacks

* Developers shouldn't rely on cleanup callbacks for essential program logic. Cleanup callbacks may be useful for reducing memory usage across the course of a program, but are unlikely to be useful otherwise.
* If your code has just registered a value to the registry, that target will not be reclaimed until the end of the current JavaScript job. See notes on WeakRefs for details.
* A conforming JavaScript implementation, even one that does garbage collection, is not required to call cleanup callbacks. When and whether it does so is entirely down to the implementation of the JavaScript engine. When a registered object is reclaimed, any cleanup callbacks for it may be called then, or some time later, or not at all.
* It's likely that major implementations will call cleanup callbacks at some point during execution, but those calls may be substantially after the related object was reclaimed. Furthermore, if there is an object registered in two registries, there is no guarantee that the two callbacks are called next to each other — one may be called and the other never called, or the other may be called much later.
* There are also situations where even implementations that normally call cleanup callbacks are unlikely to call them:
    + When the JavaScript program shuts down entirely (for instance, closing a tab in a browser).
    + When the `FinalizationRegistry` instance itself is no longer reachable by JavaScript code.
* If the target of a `WeakRef` is also in a `FinalizationRegistry`, the `WeakRef`'s target is cleared at the same time or before any cleanup callback associated with the registry is called; if your cleanup callback calls `deref` on a `WeakRef` for the object, it will receive `undefined`.
Constructor
-----------

`FinalizationRegistry()`

Creates a new `FinalizationRegistry` object.

Instance properties
-------------------

These properties are defined on `FinalizationRegistry.prototype` and shared by all `FinalizationRegistry` instances.

`FinalizationRegistry.prototype.constructor`

The constructor function that created the instance object. For `FinalizationRegistry` instances, the initial value is the `FinalizationRegistry` constructor.

`FinalizationRegistry.prototype[@@toStringTag]`

The initial value of the `@@toStringTag` property is the string `"FinalizationRegistry"`. This property is used in `Object.prototype.toString()`.

Instance methods
----------------

`FinalizationRegistry.prototype.register()`

Registers an object with the registry in order to get a cleanup callback when/if the object is garbage-collected.

`FinalizationRegistry.prototype.unregister()`

Unregisters an object from the registry.

Examples
--------

### Creating a new registry

You create the registry passing in the callback:

```js
const registry = new FinalizationRegistry((heldValue) => {
  // …
});
```

### Registering objects for cleanup

Then you register any objects you want a cleanup callback for by calling the `register` method, passing in the object and a *held value* for it:

```js
registry.register(theObject, "some value");
```

### Callbacks never called synchronously

No matter how much pressure you put on the garbage collector, the cleanup callback will never be called synchronously. The object may be reclaimed synchronously, but the callback will always be called sometime after the current job finishes:

```js
let counter = 0;
const registry = new FinalizationRegistry(() => {
  console.log(`Array gets garbage collected at ${counter}`);
});

registry.register(["foo"]);

(function allocateMemory() {
  // Allocate 50000 functions — a lot of memory!
  Array.from({ length: 50000 }, () => () => {});
  if (counter > 5000) return;
  counter++;
  allocateMemory();
})();

console.log("Main job ends");
// Logs:
// Main job ends
// Array gets garbage collected at 5001
```

However, if you allow a little break between each allocation, the callback may be called sooner:

```js
let arrayCollected = false;
let counter = 0;
const registry = new FinalizationRegistry(() => {
  console.log(`Array gets garbage collected at ${counter}`);
  arrayCollected = true;
});

registry.register(["foo"]);

(function allocateMemory() {
  // Allocate 50000 functions — a lot of memory!
  Array.from({ length: 50000 }, () => () => {});
  if (counter > 5000 || arrayCollected) return;
  counter++;
  // Use setTimeout to make each allocateMemory a different job
  setTimeout(allocateMemory);
})();

console.log("Main job ends");
```

There's no guarantee that the callback will be called sooner or if it will be called at all, but there's a possibility that the logged message has a counter value smaller than 5000.

Specifications
--------------

| Specification |
| --- |
| ECMAScript Language Specification # sec-finalization-registry-objects |

Browser compatibility
---------------------

BCD tables only load in the browser with JavaScript enabled. Enable JavaScript to view data.

See also
--------

* `WeakRef`
* `WeakSet`
* `WeakMap`


Array - JavaScript

Array
=====

The **`Array`** object, as with arrays in other programming languages, enables storing a collection of multiple items under a single variable name, and has members for performing common array operations.

Description
-----------

In JavaScript, arrays aren't primitives but are instead `Array` objects with the following core characteristics:

* **JavaScript arrays are resizable** and **can contain a mix of different data types**. (When those characteristics are undesirable, use typed arrays instead.)
* **JavaScript arrays are not associative arrays** and so, array elements cannot be accessed using arbitrary strings as indexes, but must be accessed using nonnegative integers (or their respective string form) as indexes.
* **JavaScript arrays are zero-indexed**: the first element of an array is at index `0`, the second is at index `1`, and so on — and the last element is at the value of the array's `length` property minus `1`.
* **JavaScript array-copy operations create shallow copies**. (All standard built-in copy operations with *any* JavaScript objects create shallow copies, rather than deep copies).
### Array indices

`Array` objects cannot use arbitrary strings as element indexes (as in an associative array) but must use nonnegative integers (or their respective string form). Setting or accessing via non-integers will not set or retrieve an element from the array list itself, but will set or access a variable associated with that array's object property collection. The array's object properties and list of array elements are separate, and the array's traversal and mutation operations cannot be applied to these named properties.

Array elements are object properties in the same way that `toString` is a property (to be specific, however, `toString()` is a method). Nevertheless, trying to access an element of an array as follows throws a syntax error because the property name is not valid:

```js
arr.0; // a syntax error
```

JavaScript syntax requires properties beginning with a digit to be accessed using bracket notation instead of dot notation. It's also possible to quote the array indices (e.g., `years['2']` instead of `years[2]`), although usually not necessary.

The `2` in `years[2]` is coerced into a string by the JavaScript engine through an implicit `toString` conversion. As a result, `'2'` and `'02'` would refer to two different slots on the `years` object, and the following example could be `true`:

```js
console.log(years["2"] !== years["02"]);
```

Only `years['2']` is an actual array index. `years['02']` is an arbitrary string property that will not be visited in array iteration.

### Relationship between length and numerical properties

A JavaScript array's `length` property and numerical properties are connected.

Several of the built-in array methods (e.g., `join()`, `slice()`, `indexOf()`, etc.) take into account the value of an array's `length` property when they're called.

Other methods (e.g., `push()`, `splice()`, etc.) also result in updates to an array's `length` property.

```js
const fruits = [];
fruits.push("banana", "apple", "peach");
console.log(fruits.length); // 3
```

When setting a property on a JavaScript array when the property is a valid array index and that index is outside the current bounds of the array, the engine will update the array's `length` property accordingly:

```js
fruits[5] = "mango";
console.log(fruits[5]); // 'mango'
console.log(Object.keys(fruits)); // ['0', '1', '2', '5']
console.log(fruits.length); // 6
```

Increasing the `length` extends the array by adding empty slots without creating any new elements — not even `undefined`.

```js
fruits.length = 10;
console.log(fruits); // ['banana', 'apple', 'peach', empty x 2, 'mango', empty x 4]
console.log(Object.keys(fruits)); // ['0', '1', '2', '5']
console.log(fruits.length); // 10
console.log(fruits[8]); // undefined
```

Decreasing the `length` property does, however, delete elements.

```js
fruits.length = 2;
console.log(Object.keys(fruits)); // ['0', '1']
console.log(fruits.length); // 2
```

This is explained further on the `length` page.

### Array methods and empty slots

Array methods have different behaviors when encountering empty slots in sparse arrays. In general, older methods (e.g. `forEach`) treat empty slots differently from indices that contain `undefined`.

Methods that have special treatment for empty slots include the following: `concat()`, `copyWithin()`, `every()`, `filter()`, `flat()`, `flatMap()`, `forEach()`, `indexOf()`, `lastIndexOf()`, `map()`, `reduce()`, `reduceRight()`, `reverse()`, `slice()`, `some()`, `sort()`, and `splice()`. Iteration methods such as `forEach` don't visit empty slots at all. Other methods, such as `concat`, `copyWithin`, etc., preserve empty slots when doing the copying, so in the end the array is still sparse.

```js
const colors = ["red", "yellow", "blue"];
colors[5] = "purple";
colors.forEach((item, index) => {
  console.log(`${index}: ${item}`);
});
// Output:
// 0: red
// 1: yellow
// 2: blue
// 5: purple

colors.reverse(); // ['purple', empty × 2, 'blue', 'yellow', 'red']
```

Newer methods (e.g. `keys`) do not treat empty slots specially and treat them as if they contain `undefined`. Methods that conflate empty slots with `undefined` elements include the following: `entries()`, `fill()`, `find()`, `findIndex()`, `findLast()`, `findLastIndex()`, `includes()`, `join()`, `keys()`, `toLocaleString()`, `toReversed()`, `toSorted()`, `toSpliced()`, `values()`, and `with()`.

```js
const colors = ["red", "yellow", "blue"];
colors[5] = "purple";
const iterator = colors.keys();
for (const key of iterator) {
  console.log(`${key}: ${colors[key]}`);
}
// Output
// 0: red
// 1: yellow
// 2: blue
// 3: undefined
// 4: undefined
// 5: purple

const newColors = colors.toReversed(); // ['purple', undefined, undefined, 'blue', 'yellow', 'red']
```

### Copying methods and mutating methods

Some methods do not mutate the existing array that the method was called on, but instead return a new array. They do so by first constructing a new array and then populating it with elements. The copy always happens *shallowly* — the method never copies anything beyond the initially created array. Elements of the original array(s) are copied into the new array as follows:

* Objects: the object reference is copied into the new array. Both the original and new array refer to the same object. That is, if a referenced object is modified, the changes are visible to both the new and original arrays.
* Primitive types such as strings, numbers and booleans (not `String`, `Number`, and `Boolean` objects): their values are copied into the new array.

Other methods mutate the array that the method was called on, in which case their return value differs depending on the method: sometimes a reference to the same array, sometimes the length of the new array.

The following methods create new arrays by accessing `this.constructor[Symbol.species]` to determine the constructor to use: `concat()`, `filter()`, `flat()`, `flatMap()`, `map()`, `slice()`, and `splice()` (to construct the array of removed elements that's returned).

The following methods always create new arrays with the `Array` base constructor: `toReversed()`, `toSorted()`, `toSpliced()`, and `with()`.

The following table lists the methods that mutate the original array, and the corresponding non-mutating alternative:

| Mutating method | Non-mutating alternative |
| --- | --- |
| `copyWithin()` | No one-method alternative |
| `fill()` | No one-method alternative |
| `pop()` | `slice(0, -1)` |
| `push(v1, v2)` | `concat([v1, v2])` |
| `reverse()` | `toReversed()` |
| `shift()` | `slice(1)` |
| `sort()` | `toSorted()` |
| `splice()` | `toSpliced()` |
| `unshift(v1, v2)` | `toSpliced(0, 0, v1, v2)` |

An easy way to change a mutating method into a non-mutating alternative is to use the spread syntax or `slice()` to create a copy first:

```js
arr.copyWithin(0, 1, 2); // mutates arr
const arr2 = arr.slice().copyWithin(0, 1, 2); // does not mutate arr
const arr3 = [...arr].copyWithin(0, 1, 2); // does not mutate arr
```

### Iterative methods

Many array methods take a callback function as an argument. The callback function is called sequentially and at most once for each element in the array, and the return value of the callback function is used to determine the return value of the method. They all share the same signature:

```js
method(callbackFn, thisArg)
```

Where `callbackFn` takes three arguments:

`element`

The current element being processed in the array.

`index`

The index of the current element being processed in the array.

`array`

The array that the method was called upon.

What `callbackFn` is expected to return depends on the array method that was called.

The `thisArg` argument (defaults to `undefined`) will be used as the `this` value when calling `callbackFn`. The `this` value ultimately observable by `callbackFn` is determined according to the usual rules: if `callbackFn` is non-strict, primitive `this` values are wrapped into objects, and `undefined`/`null` is substituted with `globalThis`. The `thisArg` argument is irrelevant for any `callbackFn` defined with an arrow function, as arrow functions don't have their own `this` binding.

The `array` argument passed to `callbackFn` is most useful if you want to read another index during iteration, because you may not always have an existing variable that refers to the current array. You should generally not mutate the array during iteration (see mutating initial array in iterative methods), but you can also use this argument to do so. The `array` argument is *not* the array that is being built, in the case of methods like `map()`, `filter()`, and `flatMap()` — there is no way to access the array being built from the callback function.

All iterative methods are copying and generic, although they behave differently with empty slots.

The following methods are iterative:`every()`, `filter()`, `find()`, `findIndex()`, `findLast()`, `findLastIndex()`, `flatMap()`, `forEach()`, `map()`, and `some()`.

In particular, `every()`, `find()`, `findIndex()`, `findLast()`, `findLastIndex()`, and `some()` do not always invoke `callbackFn` on every element — they stop iteration as soon as the return value is determined.

The `reduce()` and `reduceRight()` methods also take a callback function and run it at most once for each element in the array, but they have slightly different signatures from typical iterative methods (for example, they don't accept `thisArg`).

The `sort()` method also takes a callback function, but it is not an iterative method. It mutates the array in-place, doesn't accept `thisArg`, and may invoke the callback multiple times on an index.

Iterative methods iterate the array like the following (with a lot of technical details omitted):

```js
function method(callbackFn, thisArg) {
  const length = this.length;
  for (let i = 0; i < length; i++) {
    if (i in this) {
      const result = callbackFn.call(thisArg, this[i], i, this);
      // Do something with result; maybe return early
    }
  }
}
```

Note the following:

1. Not all methods do the `i in this` test. The `find`, `findIndex`, `findLast`, and `findLastIndex` methods do not, but other methods do.
2. The `length` is memorized before the loop starts. This affects how insertions and deletions during iteration are handled (see mutating initial array in iterative methods).
3. The method doesn't memorize the array contents, so if any index is modified during iteration, the new value might be observed.
4. The code above iterates the array in ascending order of index. Some methods iterate in descending order of index (`for (let i = length - 1; i >= 0; i--)`): `reduceRight()`, `findLast()`, and `findLastIndex()`.
5. `reduce` and `reduceRight` have slightly different signatures and do not always start at the first/last element.
### Generic array methods

Array methods are always generic — they don't access any internal data of the array object. They only access the array elements through the `length` property and the indexed elements. This means that they can be called on array-like objects as well.

```js
const arrayLike = {
  0: "a",
  1: "b",
  length: 2,
};
console.log(Array.prototype.join.call(arrayLike, "+")); // 'a+b'
```

#### Normalization of the length property

The `length` property is converted to an integer and then clamped to the range between 0 and 253 - 1. `NaN` becomes `0`, so even when `length` is not present or is `undefined`, it behaves as if it has value `0`.

The language avoids setting `length` to an unsafe integer. All built-in methods will throw a `TypeError` if `length` will be set to a number greater than 253 - 1. However, because the `length` property of arrays throws an error if it's set to greater than 232 - 1, the safe integer threshold is usually not reached unless the method is called on a non-array object.

```js
Array.prototype.flat.call({}); // []
```

Some array methods set the `length` property of the array object. They always set the value after normalization, so `length` always ends as an integer.

```js
const a = { length: 0.7 };
Array.prototype.push.call(a);
console.log(a.length); // 0
```

#### Array-like objects

The term *array-like object* refers to any object that doesn't throw during the `length` conversion process described above. In practice, such object is expected to actually have a `length` property and to have indexed elements in the range `0` to `length - 1`. (If it doesn't have all indices, it will be functionally equivalent to a sparse array.) Any integer index less than zero or greater than `length - 1` is ignored when an array method operates on an array-like object.

Many DOM objects are array-like — for example, `NodeList` and `HTMLCollection`. The `arguments` object is also array-like. You can call array methods on them even if they don't have these methods themselves.

```js
function f() {
  console.log(Array.prototype.join.call(arguments, "+"));
}

f("a", "b"); // 'a+b'
```

Constructor
-----------

`Array()`

Creates a new `Array` object.

Static properties
-----------------

`Array[@@species]`

Returns the `Array` constructor.

Static methods
--------------

`Array.from()`

Creates a new `Array` instance from an iterable or array-like object.

`Array.fromAsync()`

Creates a new `Array` instance from an async iterable, iterable, or array-like object.

`Array.isArray()`

Returns `true` if the argument is an array, or `false` otherwise.

`Array.of()`

Creates a new `Array` instance with a variable number of arguments, regardless of number or type of the arguments.

Instance properties
-------------------

These properties are defined on `Array.prototype` and shared by all `Array` instances.

`Array.prototype.constructor`

The constructor function that created the instance object. For `Array` instances, the initial value is the `Array` constructor.

`Array.prototype[@@unscopables]`

Contains property names that were not included in the ECMAScript standard prior to the ES2015 version and that are ignored for `with` statement-binding purposes.

These properties are own properties of each `Array` instance.

`length`

Reflects the number of elements in an array.

Instance methods
----------------

`Array.prototype.at()`

Returns the array item at the given index. Accepts negative integers, which count back from the last item.

`Array.prototype.concat()`

Returns a new array that is the calling array joined with other array(s) and/or value(s).

`Array.prototype.copyWithin()`

Copies a sequence of array elements within an array.

`Array.prototype.entries()`

Returns a new *array iterator* object that contains the key/value pairs for each index in an array.

`Array.prototype.every()`

Returns `true` if every element in the calling array satisfies the testing function.

`Array.prototype.fill()`

Fills all the elements of an array from a start index to an end index with a static value.

`Array.prototype.filter()`

Returns a new array containing all elements of the calling array for which the provided filtering function returns `true`.

`Array.prototype.find()`

Returns the value of the first element in the array that satisfies the provided testing function, or `undefined` if no appropriate element is found.

`Array.prototype.findIndex()`

Returns the index of the first element in the array that satisfies the provided testing function, or `-1` if no appropriate element was found.

`Array.prototype.findLast()`

Returns the value of the last element in the array that satisfies the provided testing function, or `undefined` if no appropriate element is found.

`Array.prototype.findLastIndex()`

Returns the index of the last element in the array that satisfies the provided testing function, or `-1` if no appropriate element was found.

`Array.prototype.flat()`

Returns a new array with all sub-array elements concatenated into it recursively up to the specified depth.

`Array.prototype.flatMap()`

Returns a new array formed by applying a given callback function to each element of the calling array, and then flattening the result by one level.

`Array.prototype.forEach()`

Calls a function for each element in the calling array.

`Array.prototype.includes()`

Determines whether the calling array contains a value, returning `true` or `false` as appropriate.

`Array.prototype.indexOf()`

Returns the first (least) index at which a given element can be found in the calling array.

`Array.prototype.join()`

Joins all elements of an array into a string.

`Array.prototype.keys()`

Returns a new *array iterator* that contains the keys for each index in the calling array.

`Array.prototype.lastIndexOf()`

Returns the last (greatest) index at which a given element can be found in the calling array, or `-1` if none is found.

`Array.prototype.map()`

Returns a new array containing the results of invoking a function on every element in the calling array.

`Array.prototype.pop()`

Removes the last element from an array and returns that element.

`Array.prototype.push()`

Adds one or more elements to the end of an array, and returns the new `length` of the array.

`Array.prototype.reduce()`

Executes a user-supplied "reducer" callback function on each element of the array (from left to right), to reduce it to a single value.

`Array.prototype.reduceRight()`

Executes a user-supplied "reducer" callback function on each element of the array (from right to left), to reduce it to a single value.

`Array.prototype.reverse()`

Reverses the order of the elements of an array *in place*. (First becomes the last, last becomes first.)

`Array.prototype.shift()`

Removes the first element from an array and returns that element.

`Array.prototype.slice()`

Extracts a section of the calling array and returns a new array.

`Array.prototype.some()`

Returns `true` if at least one element in the calling array satisfies the provided testing function.

`Array.prototype.sort()`

Sorts the elements of an array in place and returns the array.

`Array.prototype.splice()`

Adds and/or removes elements from an array.

`Array.prototype.toLocaleString()`

Returns a localized string representing the calling array and its elements. Overrides the `Object.prototype.toLocaleString()` method.

`Array.prototype.toReversed()`

Returns a new array with the elements in reversed order, without modifying the original array.

`Array.prototype.toSorted()`

Returns a new array with the elements sorted in ascending order, without modifying the original array.

`Array.prototype.toSpliced()`

Returns a new array with some elements removed and/or replaced at a given index, without modifying the original array.

`Array.prototype.toString()`

Returns a string representing the calling array and its elements. Overrides the `Object.prototype.toString()` method.

`Array.prototype.unshift()`

Adds one or more elements to the front of an array, and returns the new `length` of the array.

`Array.prototype.values()`

Returns a new *array iterator* object that contains the values for each index in the array.

`Array.prototype.with()`

Returns a new array with the element at the given index replaced with the given value, without modifying the original array.

`Array.prototype[@@iterator]()`

An alias for the `values()` method by default.

Examples
--------

This section provides some examples of common array operations in JavaScript.

**Note:** If you're not yet familiar with array basics, consider first reading JavaScript First Steps: Arrays, which explains what arrays are, and includes other examples of common array operations.

### Create an array

This example shows three ways to create new array: first using array literal notation, then using the `Array()` constructor, and finally using `String.prototype.split()` to build the array from a string.

```js
// 'fruits' array created using array literal notation.
const fruits = ["Apple", "Banana"];
console.log(fruits.length);
// 2

// 'fruits2' array created using the Array() constructor.
const fruits2 = new Array("Apple", "Banana");
console.log(fruits2.length);
// 2

// 'fruits3' array created using String.prototype.split().
const fruits3 = "Apple, Banana".split(", ");
console.log(fruits3.length);
// 2
```

### Create a string from an array

This example uses the `join()` method to create a string from the `fruits` array.

```js
const fruits = ["Apple", "Banana"];
const fruitsString = fruits.join(", ");
console.log(fruitsString);
// "Apple, Banana"
```

### Access an array item by its index

This example shows how to access items in the `fruits` array by specifying the index number of their position in the array.

```js
const fruits = ["Apple", "Banana"];

// The index of an array's first element is always 0.
fruits[0]; // Apple

// The index of an array's second element is always 1.
fruits[1]; // Banana

// The index of an array's last element is always one
// less than the length of the array.
fruits[fruits.length - 1]; // Banana

// Using an index number larger than the array's length
// returns 'undefined'.
fruits[99]; // undefined
```

### Find the index of an item in an array

This example uses the `indexOf()` method to find the position (index) of the string `"Banana"` in the `fruits` array.

```js
const fruits = ["Apple", "Banana"];
console.log(fruits.indexOf("Banana"));
// 1
```

### Check if an array contains a certain item

This example shows two ways to check if the `fruits` array contains `"Banana"` and `"Cherry"`: first with the `includes()` method, and then with the `indexOf()` method to test for an index value that's not `-1`.

```js
const fruits = ["Apple", "Banana"];

fruits.includes("Banana"); // true
fruits.includes("Cherry"); // false

// If indexOf() doesn't return -1, the array contains the given item.
fruits.indexOf("Banana") !== -1; // true
fruits.indexOf("Cherry") !== -1; // false
```

### Append an item to an array

This example uses the `push()` method to append a new string to the `fruits` array.

```js
const fruits = ["Apple", "Banana"];
const newLength = fruits.push("Orange");
console.log(fruits);
// ["Apple", "Banana", "Orange"]
console.log(newLength);
// 3
```

### Remove the last item from an array

This example uses the `pop()` method to remove the last item from the `fruits` array.

```js
const fruits = ["Apple", "Banana", "Orange"];
const removedItem = fruits.pop();
console.log(fruits);
// ["Apple", "Banana"]
console.log(removedItem);
// Orange
```

**Note:** `pop()` can only be used to remove the last item from an array. To remove multiple items from the end of an array, see the next example.

### Remove multiple items from the end of an array

This example uses the `splice()` method to remove the last 3 items from the `fruits` array.

```js
const fruits = ["Apple", "Banana", "Strawberry", "Mango", "Cherry"];
const start = -3;
const removedItems = fruits.splice(start);
console.log(fruits);
// ["Apple", "Banana"]
console.log(removedItems);
// ["Strawberry", "Mango", "Cherry"]
```

### Truncate an array down to just its first N items

This example uses the `splice()` method to truncate the `fruits` array down to just its first 2 items.

```js
const fruits = ["Apple", "Banana", "Strawberry", "Mango", "Cherry"];
const start = 2;
const removedItems = fruits.splice(start);
console.log(fruits);
// ["Apple", "Banana"]
console.log(removedItems);
// ["Strawberry", "Mango", "Cherry"]
```

### Remove the first item from an array

This example uses the `shift()` method to remove the first item from the `fruits` array.

```js
const fruits = ["Apple", "Banana"];
const removedItem = fruits.shift();
console.log(fruits);
// ["Banana"]
console.log(removedItem);
// Apple
```

**Note:** `shift()` can only be used to remove the first item from an array. To remove multiple items from the beginning of an array, see the next example.

### Remove multiple items from the beginning of an array

This example uses the `splice()` method to remove the first 3 items from the `fruits` array.

```js
const fruits = ["Apple", "Strawberry", "Cherry", "Banana", "Mango"];
const start = 0;
const deleteCount = 3;
const removedItems = fruits.splice(start, deleteCount);
console.log(fruits);
// ["Banana", "Mango"]
console.log(removedItems);
// ["Apple", "Strawberry", "Cherry"]
```

### Add a new first item to an array

This example uses the `unshift()` method to add, at index `0`, a new item to the `fruits` array — making it the new first item in the array.

```js
const fruits = ["Banana", "Mango"];
const newLength = fruits.unshift("Strawberry");
console.log(fruits);
// ["Strawberry", "Banana", "Mango"]
console.log(newLength);
// 3
```

### Remove a single item by index

This example uses the `splice()` method to remove the string `"Banana"` from the `fruits` array — by specifying the index position of `"Banana"`.

```js
const fruits = ["Strawberry", "Banana", "Mango"];
const start = fruits.indexOf("Banana");
const deleteCount = 1;
const removedItems = fruits.splice(start, deleteCount);
console.log(fruits);
// ["Strawberry", "Mango"]
console.log(removedItems);
// ["Banana"]
```

### Remove multiple items by index

This example uses the `splice()` method to remove the strings `"Banana"` and `"Strawberry"` from the `fruits` array — by specifying the index position of `"Banana"`, along with a count of the number of total items to remove.

```js
const fruits = ["Apple", "Banana", "Strawberry", "Mango"];
const start = 1;
const deleteCount = 2;
const removedItems = fruits.splice(start, deleteCount);
console.log(fruits);
// ["Apple", "Mango"]
console.log(removedItems);
// ["Banana", "Strawberry"]
```

### Replace multiple items in an array

This example uses the `splice()` method to replace the last 2 items in the `fruits` array with new items.

```js
const fruits = ["Apple", "Banana", "Strawberry"];
const start = -2;
const deleteCount = 2;
const removedItems = fruits.splice(start, deleteCount, "Mango", "Cherry");
console.log(fruits);
// ["Apple", "Mango", "Cherry"]
console.log(removedItems);
// ["Banana", "Strawberry"]
```

### Iterate over an array

This example uses a `for...of` loop to iterate over the `fruits` array, logging each item to the console.

```js
const fruits = ["Apple", "Mango", "Cherry"];
for (const fruit of fruits) {
  console.log(fruit);
}
// Apple
// Mango
// Cherry
```

But `for...of` is just one of many ways to iterate over any array; for more ways, see Loops and iteration, and see the documentation for the `every()`, `filter()`, `flatMap()`, `map()`, `reduce()`, and `reduceRight()` methods — and see the next example, which uses the `forEach()` method.

### Call a function on each element in an array

This example uses the `forEach()` method to call a function on each element in the `fruits` array; the function causes each item to be logged to the console, along with the item's index number.

```js
const fruits = ["Apple", "Mango", "Cherry"];
fruits.forEach((item, index, array) => {
  console.log(item, index);
});
// Apple 0
// Mango 1
// Cherry 2
```

### Merge multiple arrays together

This example uses the `concat()` method to merge the `fruits` array with a `moreFruits` array, to produce a new `combinedFruits` array. Notice that `fruits` and `moreFruits` remain unchanged.

```js
const fruits = ["Apple", "Banana", "Strawberry"];
const moreFruits = ["Mango", "Cherry"];
const combinedFruits = fruits.concat(moreFruits);
console.log(combinedFruits);
// ["Apple", "Banana", "Strawberry", "Mango", "Cherry"]

// The 'fruits' array remains unchanged.
console.log(fruits);
// ["Apple", "Banana", "Strawberry"]

// The 'moreFruits' array also remains unchanged.
console.log(moreFruits);
// ["Mango", "Cherry"]
```

### Copy an array

This example shows three ways to create a new array from the existing `fruits` array: first by using spread syntax, then by using the `from()` method, and then by using the `slice()` method.

```js
const fruits = ["Strawberry", "Mango"];

// Create a copy using spread syntax.
const fruitsCopy = [...fruits];
// ["Strawberry", "Mango"]

// Create a copy using the from() method.
const fruitsCopy2 = Array.from(fruits);
// ["Strawberry", "Mango"]

// Create a copy using the slice() method.
const fruitsCopy3 = fruits.slice();
// ["Strawberry", "Mango"]
```

All built-in array-copy operations (spread syntax, `Array.from()`, `Array.prototype.slice()`, and `Array.prototype.concat()`) create shallow copies. If you instead want a deep copy of an array, you can use `JSON.stringify()` to convert the array to a JSON string, and then `JSON.parse()` to convert the string back into a new array that's completely independent from the original array.

```js
const fruitsDeepCopy = JSON.parse(JSON.stringify(fruits));
```

You can also create deep copies using the `structuredClone()` method, which has the advantage of allowing transferable objects in the source to be *transferred* to the new copy, rather than just cloned.

Finally, it's important to understand that assigning an existing array to a new variable doesn't create a copy of either the array or its elements. Instead the new variable is just a reference, or alias, to the original array; that is, the original array's name and the new variable name are just two names for the exact same object (and so will always evaluate as strictly equivalent). Therefore, if you make any changes at all either to the value of the original array or to the value of the new variable, the other will change, too:

```js
const fruits = ["Strawberry", "Mango"];
const fruitsAlias = fruits;
// 'fruits' and 'fruitsAlias' are the same object, strictly equivalent.
fruits === fruitsAlias; // true
// Any changes to the 'fruits' array change 'fruitsAlias' too.
fruits.unshift("Apple", "Banana");
console.log(fruits);
// ['Apple', 'Banana', 'Strawberry', 'Mango']
console.log(fruitsAlias);
// ['Apple', 'Banana', 'Strawberry', 'Mango']
```

### Creating a two-dimensional array

The following creates a chessboard as a two-dimensional array of strings. The first move is made by copying the `'p'` in `board[6][4]` to `board[4][4]`. The old position at `[6][4]` is made blank.

```js
const board = [
  ["R", "N", "B", "Q", "K", "B", "N", "R"],
  ["P", "P", "P", "P", "P", "P", "P", "P"],
  [" ", " ", " ", " ", " ", " ", " ", " "],
  [" ", " ", " ", " ", " ", " ", " ", " "],
  [" ", " ", " ", " ", " ", " ", " ", " "],
  [" ", " ", " ", " ", " ", " ", " ", " "],
  ["p", "p", "p", "p", "p", "p", "p", "p"],
  ["r", "n", "b", "q", "k", "b", "n", "r"],
];

console.log(`${board.join("\n")}\n\n`);

// Move King's Pawn forward 2
board[4][4] = board[6][4];
board[6][4] = " ";
console.log(board.join("\n"));
```

Here is the output:
```

R,N,B,Q,K,B,N,R
P,P,P,P,P,P,P,P
 , , , , , , ,
 , , , , , , ,
 , , , , , , ,
 , , , , , , ,
p,p,p,p,p,p,p,p
r,n,b,q,k,b,n,r

R,N,B,Q,K,B,N,R
P,P,P,P,P,P,P,P
 , , , , , , ,
 , , , , , , ,
 , , , ,p, , ,
 , , , , , , ,
p,p,p,p, ,p,p,p
r,n,b,q,k,b,n,r
```

### Using an array to tabulate a set of values

```js
const values = [];
for (let x = 0; x < 10; x++) {
  values.push([2 \*\* x, 2 \* x \*\* 2]);
}
console.table(values);
```

Results in
```

// The first column is the index
0  1    0
1  2    2
2  4    8
3  8    18
4  16   32
5  32   50
6  64   72
7  128  98
8  256  128
9  512  162
```

### Creating an array using the result of a match

The result of a match between a `RegExp` and a string can create a JavaScript array that has properties and elements which provide information about the match. Such an array is returned by `RegExp.prototype.exec()` and `String.prototype.match()`.

For example:

```js
// Match one d followed by one or more b's followed by one d
// Remember matched b's and the following d
// Ignore case

const myRe = /d(b+)(d)/i;
const execResult = myRe.exec("cdbBdbsbz");

console.log(execResult.input); // 'cdbBdbsbz'
console.log(execResult.index); // 1
console.log(execResult); // [ "dbBd", "bB", "d" ]
```

For more information about the result of a match, see the `RegExp.prototype.exec()` and `String.prototype.match()` pages.

### Mutating initial array in iterative methods

Iterative methods do not mutate the array on which it is called, but the function provided as `callbackFn` can. The key principle to remember is that only indexes between 0 and `arrayLength - 1` are visited, where `arrayLength` is the length of the array at the time the array method was first called, but the element passed to the callback is the value at the time the index is visited. Therefore:

* `callbackFn` will not visit any elements added beyond the array's initial length when the call to the iterative method began.
* Changes to already-visited indexes do not cause `callbackFn` to be invoked on them again.
* If an existing, yet-unvisited element of the array is changed by `callbackFn`, its value passed to the `callbackFn` will be the value at the time that element gets visited. Removed elements are not visited.

**Warning:** Concurrent modifications of the kind described above frequently lead to hard-to-understand code and are generally to be avoided (except in special cases).

The following examples use the `forEach` method as an example, but other methods that visit indexes in ascending order work in the same way. We will first define a helper function:

```js
function testSideEffect(effect) {
  const arr = ["e1", "e2", "e3", "e4"];
  arr.forEach((elem, index, arr) => {
    console.log(`array: [${arr.join(", ")}], index: ${index}, elem: ${elem}`);
    effect(arr, index);
  });
  console.log(`Final array: [${arr.join(", ")}]`);
}
```

Modification to indexes not visited yet will be visible once the index is reached:

```js
testSideEffect((arr, index) => {
  if (index + 1 < arr.length) arr[index + 1] += "\*";
});
// array: [e1, e2, e3, e4], index: 0, elem: e1
// array: [e1, e2\*, e3, e4], index: 1, elem: e2\*
// array: [e1, e2\*, e3\*, e4], index: 2, elem: e3\*
// array: [e1, e2\*, e3\*, e4\*], index: 3, elem: e4\*
// Final array: [e1, e2\*, e3\*, e4\*]
```

Modification to already visited indexes does not change iteration behavior, although the array will be different afterwards:

```js
testSideEffect((arr, index) => {
  if (index > 0) arr[index - 1] += "\*";
});
// array: [e1, e2, e3, e4], index: 0, elem: e1
// array: [e1, e2, e3, e4], index: 1, elem: e2
// array: [e1\*, e2, e3, e4], index: 2, elem: e3
// array: [e1\*, e2\*, e3, e4], index: 3, elem: e4
// Final array: [e1\*, e2\*, e3\*, e4]
```

Inserting *n* elements at unvisited indexes that are less than the initial array length will make them be visited. The last *n* elements in the original array that now have index greater than the initial array length will not be visited:

```js
testSideEffect((arr, index) => {
  if (index === 1) arr.splice(2, 0, "new");
});
// array: [e1, e2, e3, e4], index: 0, elem: e1
// array: [e1, e2, e3, e4], index: 1, elem: e2
// array: [e1, e2, new, e3, e4], index: 2, elem: new
// array: [e1, e2, new, e3, e4], index: 3, elem: e3
// Final array: [e1, e2, new, e3, e4]
// e4 is not visited because it now has index 4
```

Inserting *n* elements with index greater than the initial array length will not make them be visited:

```js
testSideEffect((arr) => arr.push("new"));
// array: [e1, e2, e3, e4], index: 0, elem: e1
// array: [e1, e2, e3, e4, new], index: 1, elem: e2
// array: [e1, e2, e3, e4, new, new], index: 2, elem: e3
// array: [e1, e2, e3, e4, new, new, new], index: 3, elem: e4
// Final array: [e1, e2, e3, e4, new, new, new, new]
```

Inserting *n* elements at already visited indexes will not make them be visited, but it shifts remaining elements back by *n*, so the current index and the *n - 1* elements before it are visited again:

```js
testSideEffect((arr, index) => arr.splice(index, 0, "new"));
// array: [e1, e2, e3, e4], index: 0, elem: e1
// array: [new, e1, e2, e3, e4], index: 1, elem: e1
// array: [new, new, e1, e2, e3, e4], index: 2, elem: e1
// array: [new, new, new, e1, e2, e3, e4], index: 3, elem: e1
// Final array: [new, new, new, new, e1, e2, e3, e4]
// e1 keeps getting visited because it keeps getting shifted back
```

Deleting *n* elements at unvisited indexes will make them not be visited anymore. Because the array has shrunk, the last *n* iterations will visit out-of-bounds indexes. If the method ignores non-existent indexes (see array methods and empty slots), the last *n* iterations will be skipped; otherwise, they will receive `undefined`:

```js
testSideEffect((arr, index) => {
  if (index === 1) arr.splice(2, 1);
});
// array: [e1, e2, e3, e4], index: 0, elem: e1
// array: [e1, e2, e3, e4], index: 1, elem: e2
// array: [e1, e2, e4], index: 2, elem: e4
// Final array: [e1, e2, e4]
// Does not visit index 3 because it's out-of-bounds

// Compare this with find(), which treats nonexistent indexes as undefined:
const arr2 = ["e1", "e2", "e3", "e4"];
arr2.find((elem, index, arr) => {
  console.log(`array: [${arr.join(", ")}], index: ${index}, elem: ${elem}`);
  if (index === 1) arr.splice(2, 1);
  return false;
});
// array: [e1, e2, e3, e4], index: 0, elem: e1
// array: [e1, e2, e3, e4], index: 1, elem: e2
// array: [e1, e2, e4], index: 2, elem: e4
// array: [e1, e2, e4], index: 3, elem: undefined
```

Deleting *n* elements at already visited indexes does not change the fact that they were visited before they get deleted. Because the array has shrunk, the next *n* elements after the current index are skipped. If the method ignores non-existent indexes, the last *n* iterations will be skipped; otherwise, they will receive `undefined`:

```js
testSideEffect((arr, index) => arr.splice(index, 1));
// array: [e1, e2, e3, e4], index: 0, elem: e1
// Does not visit e2 because e2 now has index 0, which has already been visited
// array: [e2, e3, e4], index: 1, elem: e3
// Does not visit e4 because e4 now has index 1, which has already been visited
// Final array: [e2, e4]
// Index 2 is out-of-bounds, so it's not visited

// Compare this with find(), which treats nonexistent indexes as undefined:
const arr2 = ["e1", "e2", "e3", "e4"];
arr2.find((elem, index, arr) => {
  console.log(`array: [${arr.join(", ")}], index: ${index}, elem: ${elem}`);
  arr.splice(index, 1);
  return false;
});
// array: [e1, e2, e3, e4], index: 0, elem: e1
// array: [e2, e3, e4], index: 1, elem: e3
// array: [e2, e4], index: 2, elem: undefined
// array: [e2, e4], index: 3, elem: undefined
```

For methods that iterate in descending order of index, insertion causes elements to be skipped, and deletion causes elements to be visited multiple times. Adjust the code above yourself to see the effects.

Specifications
--------------

| Specification |
| --- |
| ECMAScript Language Specification # sec-array-objects |

Browser compatibility
---------------------

BCD tables only load in the browser with JavaScript enabled. Enable JavaScript to view data.

See also
--------

* Indexed collections guide
* `TypedArray`
* `ArrayBuffer`