0

私は本当に巨大な配列を持っています。それには何百万ものオブジェクトが含まれている可能性があり、次のようになります

    srcArray = [{
        'name': 'AAA',
        'keyA': true,
        'keyB': 'blahblah'
    }, 
    //...
    {
        'name': 'ZZZ',
        'keyA': false,
        'keyB': 'testString'
    }];

一致するすべてのオブジェクトを見つけて、別の配列に入れる必要があります。問題は、この単一の配列が大きすぎて処理できないため、メモリに入れることができないことです。アイデアは、それを小さな部分に分割し、最初の部分を取得し、何かを実行してから、次の部分に置き換えます...というように、最後の部分まで. この例を参照してください (3 つの非常に小さい部分):

パート 1、ファイルpart1.js :

    srcArray = [{
        'name': 'A1',
        'boolA': false,
        'strB': 'testString'
    }, {
        'name': 'B1',
        'boolA': false,
        'strB': 'blahblah'
    }, {
        'name': 'C1',
        'boolA': true,
        'strB': 'blahblah'
    }];

パート 2、ファイルpart2.js :

    srcArray = [{
        'name': 'A2',
        'boolA': false,
        'strB': 'blahblah'
    }, {
        'name': 'B2',
        'boolA': true,
        'strB': 'testString'
    }, {
        'name': 'C2',
        'boolA': false,
        'strB': 'blahblah'
    }];

パート 3、ファイルpart3.js :

    srcArray = [{
        'name': 'A3',
        'boolA': true,
        'strB': 'blahblah'
    }, {
        'name': 'B3',
        'boolA': false,
        'strB': 'blahblah'
    }, {
        'name': 'C3',
        'boolA': false,
        'strB': 'testString'
    }];

コード:

<!doctype html>
<html>
    <head>
        <meta charset="utf-8">
        <title>Test</title>
        <script src="jquery.min.js"></script>
        <script type="text/javascript">
            srcArray = [];
            found = [];
        </script>
        <script>
            $(document).ready(function () {
                var loadScripts = function (scripts) {
                        var result = function () {
                                delete srcArray; 
                                srcArray = undefined;
                                console.log(found);
                            }
                        var func = function (i) {
                                if (i >= scripts.length) return result();
                                var head = document.getElementsByTagName("head")[0];
                                var scr = document.createElement('script');
                                scr.src = scripts[i];
                                var f = false;
                                scr.onload = scr.onreadystatechange = function () {
                                    if (!f && (!scr.readyState || scr.readyState == "loaded" || scr.readyState == "complete")) {
                                        f = true;
                                        search('testString', srcArray);
                                        setTimeout(function () {
                                            func(++i)
                                        }, 50);
                                        scr.onload = scr.onreadystatechange = null;
                                        if (head && scr.parentNode) {
                                            head.removeChild(scr);
                                        }
                                    }
                                }
                                return head.insertBefore(scr, head.firstChild);
                            }
                        func(0);
                    }
                function search(s, arr) {
                    for (var i = arr.length; i--;) {
                        for (key in arr[i]) {
                            if (typeof (arr[i][key]) === 'string' && arr[i].hasOwnProperty(key) && arr[i][key].indexOf(s) > -1) found.push(arr[i]);
                        }
                    }
                    return found;
                };
                $('.click').click(function () {
                    delete found; 
                    found = undefined;
                    srcArray = [];
                    setTimeout(function () {
                        found = [];
                        loadScripts(["part1.js", "part2.js", "part3.js"])
                    }, 50);
                });
            });
        </script>
    </head>
    <body>
        <span class="click">click me</span>
    </body>
</html>

はい、グローバル変数が醜いことはわかっていますが、別の方法がわかりません。このコードを 10 個の部分でテストしました (各配列には 25 万個のオブジェクトが含まれていました。つまり、10 個の部分には 250 万個のオブジェクトが含まれていました。合計データ サイズは約 260MB です)。このテストを完了するのに約 20 秒かかりましたが、時間は気にしません。メモリは気にします。Firefox は、4 回のクリックで 140 MB の RAM を占有するのが最も優れていました (つまり、ブラウザは 1 GB を超えるスクリプト内で検索したことを意味します)。データ! 非常に良い結果!)、Chrome と Opera 11.52 ははるかに悪く、IE9 は最初のクリックの後に約 1GB の RAM で 2 回目のクリックで失敗しました。

質問 1. このような問題を Javascript で解決することはできますか? 巨大なデータを検索してメモリ リークを回避することは可能ですか?

質問 2. プロセスを停止するには? つまり、ある#stop要素をクリックすると、関数はその配列を停止して解放する必要がありfoundます (関数が既に見つけたのと同じ数のオブジェクトが含まれます)。

4

0 に答える 0