【 JavaScript 】変数「var」と「let」と「const」の違いについて ( ES6 )

#はじめに 【 随時更新 】
_※ 本記事の対象読者は、JS初心者の方を想定しております。_
個人的に__JavaScript(JS)のプログラミングをしていて詰まった点__について、
Qiitaの記事にしてみました。

#(1) _「 var 」_と_「 let 」_と_「 const 」_の違いについて - 2017/5/31
これまで_(ES6発表前)_、<font color="black">__JavaScript(JS)の変数宣言__</font>と言えば、__「var」__しかありませんでした。

私の知らないうち _(単純に勉強不足なだけですが)_ に、
__「let」__、__「const」__という変数宣言が標準に追加され、
__JavaScript(JS)__で使える変数宣言が、__「１」__→__<font color="red">「３」</font>__に増えました。


_これらの変数宣言は、_ <font color="red">__ES6__</font>( 2015/6～)_で追加されたものです。_

この__「ES6」__とは一体何を意味するのか？

__ES__・・・__<font color="red">「ECMAScript」</font>__
__6__・・・__<font color="red">「6th Edition」</font>__   の「略称」だそうです。

_※ ES6は、2015年6月に発表されたので、ES2015とも呼ぶみたいです。_


他の記事の対象読者は、__<font color="red">主に、「ECMAScript(ES)」に関する知識をお持ちの方</font>__ですが、
本記事では、__ECMAScript(ES)__についても詳しく記載していきたいと思います。

##そもそもECMAScript(ES)とは？
>JavaScriptの標準仕様であり、Ecma Internationalという標準化団体が標準化手続き等を行っています。[(以下、Wikipediaより抜粋)](https://ja.wikipedia.org/wiki/ECMAScript)

>|Edition (呼び方)|公開|主な変更点|
|---|---|---|
|ES1|1997/6|初版|
|ES2|1998/6|Editionとしての仕様はそのままであり、ISO/IEC 16262 international standardに完全な対応をした|
|ES3|1999/12|正規表現、よりよい文字列の取り扱い、新しいコントロール構文、try/catch例外処理、より厳格なエラー処理、数字のその他の書式化フォーマット|
|ES4|放棄|4th Editionは放棄された。言語の複雑化に関する政治的な差異による。いくつかの成果は5thの基礎として採用され、いくつかは6thの基礎となっている。|
|ES5|2011/6|"strictモード"、初期化時に発生しがちなエラーを回避するための追加仕様の追加。多くの曖昧な部分、および仕様に準拠しつつも現実世界の実装の融通の利く振る舞いを明確にした。いくらかの新機能、getterやsetter、JSONライブラリのサポート、より完全なオブジェクトの属性のリフレクション|
|ES6 or ES2015|2015/6|クラス、モジュール、イテレータ、for/ofループ、Pythonスタイルのジェネレータ、アロー関数、2進数および8進数の整数リテラル、Map、Set、WeekMap、WeekSet、プロキシ、テンプレート文字列、let、const、型付き配列、デフォルト引数、Symbol、Promise、分割代入、可変長引数|
|ES2016|2016/6|冪乗演算子、Array.prototype.includes|
|ES2017?|現在策定中||

↑表のような経緯で、__1997年6月__に初めて__「ECMAScript」__が発表されてから、
約20年間、標準化が進められており、現在も新たなバージョンES2017?を策定中のようです。

この__ECMAScript(ES)__の__6つ目のバージョン__である「__<font color="red">ES6 ( ES2015 )</font>__」で追加された、
変数宣言__「let」__、__「const」__とは何なのか？

これまでの__「var」__と何が違うのか、調べた内容をまとめてみました。

##これまでの「var」と新しく追加された「let」「const」の違い

初めての方でも理解しやすいように、簡潔に言うと、

- __「<font color="red"> let </font>」__は、__再宣言が不可能__な変数宣言
- __「<font color="red"> const </font>」__は、__再宣言__と__再代入が不可能__な変数宣言

_※ 従来の__「var」__では、<font color="red">「再宣言」</font>も<font color="red">「再代入」</font>も可能でした。_

## 「let」、「const」はなぜ追加されたのか？
従来の変数定義である__「var」__では、__<font color="red">「1.誤って変数を2重に定義」</font>__してしまったり、
__<font color="red">「2.代入したくない変数(定数)などに再代入」</font>__するといったようなプログラム上の予期せぬ不具合(バグ)が
どうしても起きてしまう場面がありました。

_こうした問題を変数を宣言する段階から取り除こうと追加されたのが、「let」、「const」です。_

専門用語？を使って表現すると、下記2つの挙動が従来の宣言「var」とは異なります。

1. __ブロックスコープ[^1]__が有効になるということ
2. [変数の巻き上げ(hoisting)](http://analogic.jp/hoisting/)[^2]の挙動がこれまでの__「var」__と異なるということ

じゃこれから、JavaScript(JS)でプログラミングする時は、
どの変数宣言をどういう場合に使えば良いの？とお思いの方が、多数いらっしゃると思います。

_※ 私自身、本記事を執筆しようとしたキッカケが上記理由です。
プログラミング経験が浅い方ならだれもが疑問に思う点だと思います。_

__<font color="red">JavaScript(JS)初心者の方</font>__でもこれだけ覚えておくだけで、
__「let」__と__「const」__の使い分けができる__簡単なTips__をご用意しました。

## 「let」と「const」の使い分け方 (Tips)

__再代入が必要な場合のみ__、<font color="red">__「 let 」__</font>を使用し、
__それ以外の変数__は、<font color="red">__「 const 」__</font>で定義することによって、
さきほど上記でご説明させていただいたような__不具合(バグ)__を
__<font color="red">未然に防ぐことができる</font>__と思います。

_また、従来の<font color="red">「 var 」</font>に関しては、さまざまなサイトを拝見させていただきましたが、
どのサイトでも利用する理由が見当たらないので、今後は使用しないというような記載ばかりでした。_




#おわりに

少し本記事の執筆経緯について、お話したいと思います。

## 「Qiitaの及川氏が考えるエンジニアの成長に必要なアウトプット」

>(以下、記事より抜粋)

>![Qiitaの良いところ](http://ascii.jp/elem/000/001/216/1216802/DSC_3577_480x360_480x360.jpg)
最初から正しい投稿でなくとも、とにかく挙げてみる。
__Article : [Qiitaの及川氏が考えるエンジニアの成長に必要なアウトプット](http://ascii.jp/elem/000/001/216/1216127/)__

###「最初から正しい投稿でなくとも、とにかく挙げてみる。」

_最近、「 <font color="red">Qiita記事の質が落ちた</font> 」とか、、
「 <font color="red">もっと調べてから書け！</font> 」といったようなコメントもちらほら見かける中で、
この記事を読んで、自分のような低レベルなエンジニアこそQiitaを
もっとうまく活用すべきだ！と思うようになりました。_

写真のスライドにも記載がある通り、__Qiitaの良いところ__ は、

<font color="red">__「投稿する記事の内容が必ずしも高いレベルである必要が無い」__</font>という点です。

_(※ 決してQiitaの回し者ではありません。)_

###「投稿する上で個人的に気をつけようと思ったこと。」

もちろん、投稿する以上は、自分が正しいと思って書いている訳ですが、人間なので間違うこともあります。

__間違った情報を読者のみなさまに共有してしまう危険性もある__と思います。

しかしながら、__<font color="red">まずはアウトプットをしてみる</font>__ことで、
__<font color="red">自分自身のエンジニアとしての価値(社外での評価)</font>__も明確になりますし、
万が一記事内容に誤りがあれば、Qiitaのコミュニティがコメント等のフィードバックを通じて気づきを与えてくれると思います。

### 「アウトプットから成長を考える」

- __【Output】__ex._「Qiita」に記事を投稿すること。_ <font color="red">__(最終ゴール：目標設定)__</font>
- __【Input】__ _どういったインプットをする必要があるのか？_ <font color="red">__(今すべきこと)__</font>

>[(以下、記事より抜粋)](http://ascii.jp/elem/000/001/216/1216127/)

>及川氏は__「アウトプットから成長を考える」__ことが開発者にとって必要だと力説する。「SECIモデルでの共同化、表出化、連結化を回すのは、自分の持っているモノを外にはき出すアウトプットそのもの。これを行うことで、知識が拡がっていく」

#### 【 結果 - エンジニアとしての成長スピードが格段にアップする。 】

最後までお読みいただき、ありがとうございました。
この記事自体も__随時更新__を行っていきたいと考えておりますので、
もしよろしければ__「いいね！」__をよろしくお願いいたします。

####__[2017/06/01 追記]__
みなさんが「いいね」を押してくださったおかげで、
__「Popular Items」__にランクインすることができました！
Qiitaの記事は最近書き始めましたが、大変嬉しいです(^^)/

記事の更新の方も頑張りますので、引き続きよろしくお願いします！

>![image.png](https://qiita-image-store.s3.amazonaws.com/0/180432/ab407480-f447-fe67-ed21-e25ab2f6aca3.png)


[^1]: スコープとは、変数を参照できる範囲のこと。スコープ外の変数にはアクセスができない。

[^2]: JavaScriptでは、関数内のどこにでもvar文を使用して変数を宣言することができます。そして、これらの変数は関数内のいかなる場所で宣言されたとしても、その関数の先頭で宣言されたのと同じように動作します。このような振る舞いのことを「変数の巻き上げ(hoisting)」と呼びます。