ユーザ用ツール

サイト用ツール


ecmascript:generator

差分

このページの2つのバージョン間の差分を表示します。

この比較画面へのリンク

次のリビジョン
前のリビジョン
ecmascript:generator [2015/10/24 04:29] – 作成 nullponecmascript:generator [2025/09/15 15:59] (現在) nullpon
行 1: 行 1:
 ====== Generator ====== ====== Generator ======
  
-Generator(ジェネレータ)はECMAScript 6で追加され新機能+Generator(ジェネレータ)関数[[./iteration|反復処理プロトコル]]を実装し特別なGeneratorオブジェクトを返す特別な関数
  
-ジェネレータは、内部の状態管理が必要とるIterator(イテレタ)の反復処理において、オブジェクトよりも簡単・安全に状態管理を行うための機能である。 +ジェネレータは、特別ド''yield''指定した値がイテレータプロトコルおけ''value''値となる。
- +
-ジェネレタを用いた反復処理は「次の値の取り出し」と「取り出した値の処理」交互に繰り返される。「次の値の取り出し」を行った後「取り出した値の処理」が完了するまでジェネレータ関数記述された手続きの流れが一時中断され。 +
- +
-今までJavaScriptでは実現できかった手続き途中での中断という動作が非同期処理のより良いコーディング手法として注目されている。+
  
 ===== ジェネレータの動作 ===== ===== ジェネレータの動作 =====
  
 <code javascript> <code javascript>
-function* f(i) { +function* generator() { 
-  var y; +  yield 1
-  y = yield ++i+  yield 2
-  console.log(y);        // => "a" +  yield 3;
-  y = yield ++i+
-  console.log(y);        // => "b" +
-  y = yield ++i; +
-  console.log(y)       // => "c"+
 } }
  
-var g = f(1);               // g => [Object: generator] 
-console.log(g.next());      // => { value: 2, done: false } 
-console.log(g.next("a"));   // => { value: 3, done: false } 
-console.log(g.next("b"));   // => { value: 4, done: false } 
-console.log(g.next("c"));   // => { value: undefined, done: true } 
-</code> 
- 
-  - キーワード ''function*'' でジェネレータ関数を定義 
-  - ジェネレータ関数を実行するとGeneratorオブジェクトが得られる 
-    * この時点ではジェネレータ関数の中身は実行されない 
-    * 引数 1 はジェネレータ関数に渡される 
-  - Generator#next が呼ばれると、ジェネレータ関数の最初の yield 式まで実行される。 
-    * Generator#next が ''{ value: 2, done: false }'' (valueはyield式の評価結果)を返す 
-  - 再度 Generator#next が呼ばれる 
-    * 最初の yield が next の引数("a")を返す 
-    * ジェネレータ関数が次の yield 式まで実行される。 
-    * Generator#next が ''{ value: 3, done: false }'' を返す。 
-  - 再度 Generator#next が呼ばれる 
-    * 二番目の yield が next の引数("b")を返す 
-    * ジェネレータ関数が次の yield 式まで実行される。 
-    * Generator#next が ''{ value: 4, done: false }'' を返す。 
-  - さらに Generator#next が呼ばれる。 
-    * 三番目の yield が next の引数("c")を返す。 
-    * ジェネレータ関数の末尾まで実行される。 
-    * Generator#next が ''{ value: undefined, done: true }'' を返す。 
  
 +for (const i of generator()) {
 +   console.log(i)  // => 1, 2, 3
 +}
 +</code>
 ===== ジェネレータの例 ===== ===== ジェネレータの例 =====
  
行 53: 行 24:
  
 <code javascript> <code javascript>
-function* fibonacci(limit = Infinity) { +function* fibonacci(count = Infinity) { 
-    var count = 0; +    let a = 1b = 1 
-    var a = 1+    for (let i = 0; i < count; i++) { 
-    var b = 1; +        yield a; 
-    while(count++ < limit) { +        [a, b] [b, a + b]
-        let c = + b+
-        a = b+
-        = c; +
-        yield c;        +
     }     }
 } }
  
-for (let i of fibonacci(5)) { +for (let i of fibonacci(10)) { 
-   console.log(i)+   console.log(i);   // => 1, 1, 2, 3, 5, 8, 13, 21, 34, 55
 } }
 +
 </code> </code>
-結果 +
-<code> +
-+
-+
-+
-+
-13 +
-</code>+
  
 Rangeを生成するジェネレータ Rangeを生成するジェネレータ
行 88: 行 49:
  
 for (let i of range(3,7)) { for (let i of range(3,7)) {
-   console.log(i)+   console.log(i);  // => 3, 4, 5, 6, 7
 } }
 </code> </code>
-結果 
-<code> 
-3 
-4 
-5 
-6 
-7 
-</code> 
- 
-===== 非同期処理 ===== 
- 
-ジェネレータを用いた非同期処理 
- 
-<code javascript> 
-var g = (function* () { 
-   console.log(1); 
-   var x = yield setTimeout(function() { console.log(2); g.next(3); }, 1000); 
-   console.log(x); 
-   var y = yield setTimeout(function() { console.log(4); g.next(5); }, 2000); 
-   console.log(y); 
-})(); 
-g.next(); 
-</code> 
-結果 
-<code> 
-1  // ここで1秒待つ 
- 
-3  // ここで2秒待つ 
-4 
-5 
-</code> 
- 
ecmascript/generator.1445660989.txt.gz · 最終更新: by nullpon