2
if(true) {
  tmp = 'abc';
  console.log(tmp);//which should throw referenceError but not

  let tmp;
  console.log(tmp);

  tmp = 123;
  console.log(tmp);
}

このコードの結果は

abc
undefined
123

最初の console.log(tmp) がエラーをスローしないのはなぜですか?


なぜ referenceError をスローする必要があるのか

ECMAScript 2015 では、let は変数をブロックの先頭に持ち上げます。ただし、変数宣言の前にブロック内の変数を参照すると、ReferenceError が発生します。変数は、ブロックの開始から宣言が処理されるまでの「一時的なデッド ゾーン」にあります。


問題はバブルの設定だと思います。
ということはbabelのバグでしょうか? https://github.com/babel/babel.github.io/issues/826

4

3 に答える 3

2

おっしゃる通り、ES6 では例外がスローされます。あなたに向いていない理由は2つあります。

  • node.js は既に実装されていますletが、strict モードでのみ正しく動作します。あなたはそれを使うべきです。
  • デフォルトでは、babel は TDZ をトランスパイルしていないように見えます。TDZ は非常に複雑で、コードが長くなるからです。es6.blockScopingTDZただし、 /オプションを使用して有効にすることもできes6.spec.blockScopingます (ただし、これが Babel 5 でのみ機能したのか、Babel 6 で何が起こったのかはわかりません)。
于 2016-06-12T15:33:05.983 に答える
0

声明

tmp = 'abc';

エレガントではありませんが、通常モードでは問題ありません (厳密モード以外では許可されていないletキーワードを除く)。グローバル変数を作成するだけです。ただし、コードは正しくなく、このコードを「厳密モード」で実行した場合にのみエラーがスローされます。このモードでは、次のキーワードのいずれかを使用してすべての変数を宣言する必要があります。

  • 変数
  • させて
  • 定数

'use strict'
if(true) {
  tmp = 'abc';
  console.log(tmp);//which should throw referenceError and now it does
                  
  let tmp;
  console.log(tmp);

  tmp = 123;
  console.log(tmp);
}

于 2016-06-12T15:21:09.287 に答える
-2

いいえ、参照エラーをスローするべきではありません。

変数は、割り当て時に (グローバル スコープで) 暗黙的に宣言されます。

その後、同じ名前でスコープがより狭い新しい変数を宣言します。を使用して宣言されているため、新しい変数は巻き上げられませんlet

参照エラーが発生するはずだと思う理由を説明していないため、これ以上正確な答えを出すことはできません。

于 2016-06-12T14:56:01.957 に答える