読者です 読者をやめる 読者になる 読者になる

Panda Noir

JavaScript の限界を究めるブログです。

C++のIterator学んだらJavaScriptのIterator理解できた

(この記事はQiitaで僕が書いたものを移行した記事です。記事中のコメントはQiitaの該当記事を参照ください)

C++ 入門書の次に読む本」という本を読み終わりました。中身はとても良かったです。まあ書評は置いときます。この本にIteratorが出てきたので、そういえばJavaScriptにもES6から実装されるんだっけと思い出し、改めて見てみたらすんなりと理解できた話

追記: オブジェクトはiterableでないようです。以下の記事は修正してませんがそのつもりで読んでください。

Iteratorの何が嬉しいのか

イテレータ」として抽象化できることです。 つまり、オブジェクト用、配列用、文字列用と関数を分けて作る必要がなくなります。 こんな感じ

function find(iter, key){
    for (let i = iter.next(); !i.done(); i = iter.next();) {
        if (i.value === key) return true;
    }
    return false;
}

こう書けます。この関数はイテレータ向けのアルゴリズムなのでイテレータならばどんなデータ型でも対応できます。 オブジェクト、配列、文字列全て対応できてますね。

自作イテレータもライブラリ提供のイテレータでもお構いなし。さいつよですね。

findだけでなくlengthやmap、each、とにかく何でもこれでさばけます。さいつよですね。

ちなみに上ではC++っぽくfor書いてますが for (var i of iter) でもOKです。さいつよですね。

function find(iter, key){
    for (const i of iter) {
        if (i === key) return true;
    }
    return false;
}

イテレータさいつよfind関数がさらにさいつよに(哲学

独自イテレータを作るときはGeneratorがさいつよかも。

下は素数を返す独自イテレータ。こんなことができるのも魅力だね。

function* primeIterator() {
    for (let i = 2;; i++) {
        if (isPrime(i)) yield i;
    }
    function isPrime(n) {
        for (let i = 2; i * i <= n; i++) {
            if (n % i === 0) return false;
        }
         return true;
    }
}