const
=====

**`const`** 宣言はブロックスコープのローカル変数（定数）を宣言します。定数の値は代入演算子を使用して再代入することができませんが、定数がオブジェクトであった場合、そのプロパティを追加したり、更新したり、削除したりすることができます。

試してみましょう
--------

構文
--


```js
const name1 = value1;
const name1 = value1, name2 = value2;
const name1 = value1, name2 = value2, /\* …, \*/ nameN = valueN;
```


`nameN`

宣言する変数名。それぞれ、正当な JavaScript 識別子または分割結合パターンでなければなりません。

`valueN`

変数の初期値。正式な式であれば何でもかまいません。

解説
--

`const` 宣言んは `let` とよく似ています。

* `const` declarations are scoped to blocks as well as functions.
* `const` 宣言は宣言した位置に到達してからでないとアクセスすることができません（一時的デッドゾーンを参照してください）。このため、 `const` 宣言は一般的に巻き上げされないと見なされます。
* スクリプトの最上位で宣言された場合、 `const` 宣言は `globalThis` にプロパティを作成しません。
* `const` 宣言は、同じスコープ内の他の宣言によって再宣言することはできません。
* `const` は文ではなく宣言を始めます。つまり、ブロックの本体として単独の `const` 宣言を使用することはできません（変数にアクセスする方法がないので、意味はあります）。

```js
if (true) const a = 1; // SyntaxError: Lexical declaration cannot appear in a single-statement context
```


定数の初期化子が必要です。同じ宣言の中でその値を指定しなければなりません。（後で変更できないことを考えると、これは意味のあることです。）


```js
const FOO; // SyntaxError: Missing initializer in const declaration
```


`const` 宣言は値への不変の参照を作成します。これはその値が不変であるという意味ではなく、変数の識別子が再割り当てできないという意味です。例えば、内容がオブジェクトの場合、これはオブジェクトの内容（例えばプロパティ）は変更できることを意味しています。 `const` 宣言は「アイデンティティが一定の変数を作成する」のであって、「値が一定の変数を作成する」のではありません。また、「不変のバインド」を作成するのであって、「不変の値」を作成するのではありません。

多くのスタイルガイド（MDN のものも含む）では、変数がそのスコープで再代入されない場合は、 `const` を `let` の代わりに使用することを推奨しています。これにより、変数の型（プリミティブの場合は値）が変更されることはないという意図が明確になります。他にも、プリミティブ以外の変数が変更される場合は `let` を推奨する人もいます。

`const` キーワードに続くリストはバインディングリストと呼ばれ、カンマで区切られます。カンマはカンマ演算子ではなく、 `=` は代入演算子ではありません。後の変数の初期化子は、リスト内の前の変数を参照することができます。

例
-

### 基本的な定数の使い方

定数は大文字または小文字で宣言することができますが、特にプリミティブの場合は、本当に変更不可能であるので、すべて大文字で宣言するのが慣例です。


```js
// MY\_FAV を定数として定義して、その値を 7 にします
const MY\_FAV = 7;

console.log("my favorite number is: " + MY\_FAV);
```



```js
// Re-assigning to a constant variable throws an error
MY\_FAV = 20; // TypeError: Assignment to constant variable

// Redeclaring a constant throws an error
const MY\_FAV = 20; // SyntaxError: Identifier 'MY\_FAV' has already been declared
var MY\_FAV = 20; // SyntaxError: Identifier 'MY\_FAV' has already been declared
let MY\_FAV = 20; // SyntaxError: Identifier 'MY\_FAV' has already been declared
```

### ブロックスコープ

ブロックスコープの性質に注意することが重要です。


```js
const MY\_FAV = 7;

if (MY\_FAV === 7) {
  // これは問題なく、ブロックスコープの MY\_FAV 変数を作成します
  const MY\_FAV = 20;
  console.log(MY\_FAV); // 20

  // これはグローバルコンテキストに巻き上げられ、エラーが発生します
  var MY\_FAV = 20; // SyntaxError: Identifier 'MY\_FAV' has already been declared
}

console.log(MY\_FAV); // 7
```

### オブジェクトと配列の定数

`const` はオブジェクトや 配列にも作用します。オブジェクトを上書きしようとすると、"Assignment to constant variable" というエラーが発生します。


```js
const MY\_OBJECT = { key: "value" };
MY\_OBJECT = { OTHER\_KEY: "value" };
```


しかし、オブジェクトのキーは保護されていないので、次の文は問題なく実行されます。


```js
MY\_OBJECT.key = "otherValue";
```


オブジェクトを不変にするには、 `Object.freeze()` を使用する必要があります。

配列も同様です。新しい配列を変数に割り当て要とすると、"Assignment to constant variable" のエラーが発生します。


```js
const MY\_ARRAY = [];
MY\_ARRAY = ["B"];
```


しかし、配列にアイテムを追加することはでき、変更は可能です。


```js
MY\_ARRAY.push("A"); // ["A"]
```

### 分割代入による宣言

それぞれの `=` の左辺はバインドパターンにもなります。これにより、一度に複数の変数を作成することができます。


```js
const result = /(a+)(b+)(c+)/.exec("aaabcc");
const [, a, b, c] = result;
console.log(a, b, c); // "aaa" "b" "cc"
```


詳しくは、分割代入を参照してください。

仕様書
---

| Specification |
| --- |
| ECMAScript Language Specification # sec-let-and-const-declarations |

ブラウザーの互換性
---------

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

関連情報
----

* `var`
* `let`
* JavaScript ガイドの定数