文系大学生がJavaScriptを旅する(2)〜letとconstとvarの使い分け〜

##変数と定数

さて、[前回の記事](https://qiita.com/okitsu090807/items/6394192df524244d2582)から私のJavaScriptの旅が始まったのだが、JavaScriptを旅するにあたって,
私がまず最初に取り上げたい話題は、**「let, const, var」**である。これは初学者あるあるだと勝手に思い込んでいるのだが、皆さん「定める値＝変数」という思い込みをしていた時期は無いだろうか？私はあった。なので変数と定数を使い分ける意味自体が理解できなかったのだ。

今回は変数と定数が一体何なのか、そして「let, const, var」の使い分けを私なりにまとめていきたい。そして、私と同じ様な悩みを抱えている人にこの記事が届くことを祈っている。そんな事はとっくに知っているという方は初学者の気持ちを学ぶ感覚で読んでいただきたい。

###変数

```javascript
//変数「name」にオキツを代入する
 let name = 'オキツ';

//変数「blog」にオキツのブログを代入する
 var blog = 'オキツのブログ';
```

多くの人は、JavaScriptで変数を使う時は**let**を使うだろう。varも変数を扱う場合に使用できるが、現在使われることは少なくなっている。varに関しては後述するのでそちらを見ていただきたい。
これは定数にも言えることなのだが、用語として変数（定数）に値を当てはめることを**「値を代入する」**又は**「値を格納する」**という。

私事なのだが、「格納する」という表現は中々どうして慣れない。これはプログラミング関係の用語に共通して言えるのだが、難しい言葉が多くないだろうか。まあ、ぐだぐだ言ってもしょうがないのでコツコツ覚えていくしかないのだが。

おっと、話が逸れてしまって申し訳ない。変数は再代入可能な値を使いたい時に用いるという。正直な話、「再代入可能な値を用いる時に変数を使うよ！」と言われても、いつ使うのだろうというのが正直な感想だと思う。なので、以下に変数（再代入可能な値）を使用する典型的な例（主観）を挙げる。

```javascript

const name = ['オキツ１','オキツ２'];

for(let i=0; i < name.length; i++ ){
 console.log(i);
 console.log(name);
}

```

#####出力結果

<img width="485" alt="スクリーンショット 2020-04-26 16.50.38.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/404639/97dc42df-e4e6-728c-e8a7-1ee9f263952e.png">

上の出力結果を見てもらうと分かるように**letに代入した変数iの値が変わっている**。for文の説明は今回の趣旨から逸れるので省かせてただくことを了承願いたい。

しかし、letは再代入が可能なのだが**再度宣言することができない**ことを同時に覚えておいていただきたい。

```javascript

//再代入は問題ない
let name = 'オキツ '
name = 'okitsu';

//再宣言は不可能
let name = 'オキツ';
let name = 'okitsu';//ここでエラーが出る

```

#####let再宣言時のエラー文

<img width="489" alt="スクリーンショット 2020-04-27 22.32.26.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/404639/cd56a0e6-45b6-276f-56dd-eb96b6e70c6e.png">

私の親愛なるMacbookに**「すでに宣言されてますよ」**と怒られてしまった。letは再宣言不可能ということを私の身を以て伝えることができただろうか。あとでMacbookには謝っておくとしよう。

要するに私がここで言いたかったことは、letに代入した値は再代入可能であるが、再宣言不可能ということである。それ以上でもそれ以下でも無いと私は思うのだが、真実は1つでは無いのかもしれない。もし、もう一つの真実を教えてくれる方がいたらご教授願いたい限りである。


###定数

```javascript

//定数nameにオキツを代入する
const name = 'オキツ';
```

値を代入するにあたって基本的にやることは使う英単語がletからconstに変わったくらいである。だからこそ、初学者にとっては**どっちでも良いんじゃね感**がプンプンするのである。

さて、みなさん変数(let)と定数(const)の明確な違いを覚えていらっしゃるだろうか？忘れてしまったという方はご安心を。人間というのは存外物忘れをする生き物である。

さて、定数の最大の特徴は**再代入が不可能**という点ではないだろうか。私もconstは再代入不可能という説明は耳にタコができるほど聞いてきたが実際の使い分けとなるとチンプンカンプンであった。なので私はめげずに再代入を試みてみた。トライ・アンド・エラーこそエンジニアの醍醐味であろう。

```javascript

//定数nameにオキツを代入
const name = 'オキツ';
console.log(name);

//nameにokitsuを再代入しようとする
name = 'okitsu';
console.log(name);

```

#####出力結果

![スクリーンショット 2020-04-26 19.23.30.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/404639/0223a64a-36ce-0714-d0c7-db814692c0be.png)

定数に再代入を試みた結果、またMacbookに怒られてしまった。私の小さな抵抗は一行の英文によってかき消されたのだ。いや、かき消されたのではない。経験値へと昇華されたのだ。うん。

このエラー文には**「定数に値入れるべからず」**的なことが書いてある。これで、私が何度も言っているように定数に値は再代入できないことが実践的に理解していただけたと思う。私は再代入する予定が無い値を定める時は定数（const）を使うようにしている。定数を用いることで、うっかり同じ名前で定数を定義してしまってもエラーが出るため、自分の過ちに気付けるのだ。letを使ってしまうと気づかないうちに値が上書きされてしまい、予期せぬ挙動を起こしてしまう可能性があるのだ。ちなみに、constもletと同様に**再宣言が不可能**ということも覚えておいていただきたい。

##変数var

さて、ここまで変数と定数について綴ってきたが、そろそろ先程話しを保留にしておいたvarについて私の経験談も踏まえて話していこうと思う。

###varとの決別

プログラミングをはじめた頃の私は変数と定数の違いがわからなかった。正直なところ、全部varでいいのではないかとも思っていた。そんな私の元に一通の手紙が届いた。

**「汝、varを使うべからず。constとletを使うべし。」**

今頃、手紙を使う人がいるのかと一種の驚きの気持ちを抱きながら、この手紙をきっかけに私はなんとなくvarを使うことをやめた。その手紙にはやめるべき理由は書いていなかったが、確かに周りの人は使っていないかった。いたって日本人らしい集団迎合的な考え方で私はvarを使うことをやめたのである。

しかし、私も一年ほどプログラミングをやってきた身なのでそろそろvarを多くの人が使わない謎を解いていきたいと思う。

###varの謎に迫る

私はGoogleという名の海へ航海に出た。まだ見ぬ発見を目指した大航海時代の船人たちの気持ちに寄り添えるのではないかというほどに、長い旅をした気がする。そして、私は一つの答えにたどり着くことができた。

```javascript

var name = 'okitsu';

const blog = () => {
  console.log(name);
  var name = 'オキツ';
  console.log(name);
}

blog();

```

#####出力結果

<img width="481" alt="スクリーンショット 2020-04-27 22.07.46.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/404639/40600b82-529b-db0d-4dab-7d80444a3725.png">

これが私がたどり着いた、**varを多くの人が使わない理由**である。変数nameを定義していたはずなのに、blogという関数の中で一回目に呼び出した時は**undefind**になっている。これはどういうことだろうか。私の存在が私の愛用しているMacbookから否定されてしまったのだろうか。

これは決して私のMacbookがツンデレなのではなく、JavaScriptの然るべき挙動であるので、読者の皆さんは安心していただきたい。varの特徴として、関数の中で使用された場合に変数が関数の中で再定義されてしまうのである。なので実際、関数の中で行われている動きとしては、

```javascript

var name = 'okitsu';

const blog = () => {

  var name;//これはundefindを出力する

  console.log(name);
  var name = 'オキツ';
  console.log(name);
}

blog();

```

ということが行われているのである。確かに、これは予期せぬエラーを生んでしまいかねない。私が言っていることがあまり理解できないという方は、とりあえず**varを安易に使用することで、面倒なことが起こり得る**ということだけでも是非覚えて帰っていただきたい。

##今回のまとめ

さて、ここまで変数と定数、そしてvarが使われない理由を綴ってきた。この記事を通じて、一人でも多くの方がJavaScriptの理解を少しでも深めたり、初学者の気持ちに寄り添えることができたなら幸いである。

また、個人ブログを先日開設したのでこちらもチェックしていただけると感無量であります。
それでは、最後まで読んでいただきありがとうございました。