質問するログイン新規登録

回答編集履歴

1

`setTimeout` のコールバック関数をネストしない `forLoop3` を追記。ブロックスコープの説明を一文追記。

2019/06/22 02:54

投稿

think49
think49

スコア18194

answer CHANGED
@@ -4,22 +4,32 @@
4
4
  原始的なコードは応用が利く分、発想の幅が広がります。
5
5
 
6
6
  - for 文よりも原始的な while 文で再現
7
- - for 文のブロックスコープは関数スコープで再現 ([Lhankor_Mhy さんが指摘されている性質](https://teratail.com/questions/196133#reply-291017))
7
+ - for 文のブロックスコープは関数スコープで再現。関数 `forLoop*` に引数 `i` (= `j`, `k`) が渡されると、**複製された変数 i は関数スコープになる**ので、関数外からの干渉を受けません。 ([Lhankor_Mhy さんが指摘されている性質](https://teratail.com/questions/196133#reply-291017))
8
8
 
9
9
  ```JavaScript
10
10
  'use strict';
11
+ function handleTimeout (characters, k) {
12
+ const character = characters[k];
13
+ console.log(`${character.name}`);
14
+ }
15
+
11
16
  function forLoop1 (i) {
12
17
  const character = characters[i];
13
18
  console.log(`${character.name}`);
14
19
  }
15
20
 
16
- function forLoop2 (i) {
21
+ function forLoop2 (j) {
17
22
  setTimeout(function handleTimeout () { // 分かりやすさ重視で関数をネストさせていますが、毎回、関数を生成するのは無駄なので、基本的には関数を外に追い出す事を推奨します
18
- const character = characters[i];
23
+ const character = characters[j];
19
24
  console.log(`${character.name}`);
20
25
  }, 100);
21
26
  }
22
27
 
28
+ function forLoop3 (k) { // 関数 handleTimeout を外に追い出した場合
29
+ setTimeout(handleTimeout, 100, characters, k);
30
+ }
31
+
32
+
23
33
  const characters = [
24
34
  {name: "田中", age: 14},
25
35
  {name: "佐藤", age: 100},
@@ -38,10 +48,20 @@
38
48
  forLoop2(j); // "田中" -> "佐藤" -> "久保" -> "飯田"
39
49
  j++;
40
50
  }
51
+
52
+ let k = 0;
53
+ while (k < characters.length) {
54
+ forLoop3(k); // "田中" -> "佐藤" -> "久保" -> "飯田"
55
+ k++;
56
+ }
41
57
  ```
42
58
 
43
- BabelのES5コンパイルも似たようなコードを生成していた記憶があります。
59
+ BabelのES5コンパイルも似たようなコードを生成していた記憶があります。
44
60
 
45
61
  - [Babel · The compiler for next generation JavaScript](https://babeljs.io/)
46
62
 
63
+ ### 更新履歴
64
+
65
+ - 2019-06-22 11:54:16 `setTimeout` のコールバック関数をネストしない `forLoop3` を追記。ブロックスコープの説明を一文追記。
66
+
47
67
  Re: Sano さん