アナログES 5 Array.prototype.reduce

7940 ワード

一.前言
教主ブログのヒントを得て、reduceをサポートしていないブラウザでこの関数をシミュレートすることにしました.ここでまずクッションを作ります.
1.配列内のundefinedとピット
var a = [undefined,,2];

a[3] = undefined;

a[100] = 99;// 



a[0] === undefined;//true

a[1] === undefined;//true

a[3] === undefined;//true

a[50] === undefined;//true



0 in a;//true

1 in a;//false

3 in a;//true

50 in a; //false

私はa[1]とa[50]という明示的な付与のない要素を「坑」と呼び、坑父の坑~
 
2. 
 
二.コード#コード#
1.バージョン1
for(var i=0,l=arr.length;i// reduce if(! Array.prototype.reduce) { Array.prototype.reduce = function(f , initValue){ var i = bg = ret = null , ed = this.length ? this.length : 0;// if(this.length === 0 && arguments.length < 2){ // throw new TypeError('TypeError: Inside Array.prototype.reduce , lack of valid parameter'); }else if(arguments.length >= 2){ // , initValue, initValue this[0] bg = 0; ret = initValue; }else{ // , initValue, this[0] this[1] bg = 1; ret = this[0]; } for(i=bg; i<ed; i++) { // this[i] if(i in this){ ret = f(ret , this[i] , i , this); } } return ret; }; }
このバージョンの問題は、疎配列に対処する効率が極めて低いことであり、例えばvar a=[0]である.a[100000] = 10000; この配列の要素の和を求めるために,使用方法1では,9999回が浪費された10000回のループが実行される.
 
 
2.バージョン2
for in構造を用いて配列を遍歴し,疎配列に効率的に対応できる
//  reduce

if(! Array.prototype.reduce)

{

    Array.prototype.reduce = function(f , initValue){



        if(this.length === 0 && arguments.length < 2){

            //

            throw new TypeError('TypeError: Inside Array.prototype.reduce , lack of valid parameter');

        }

        var i = 0,//

            p = null,//property ,  

            r = /(^0$)|(^[1-9]\d*$)/,//  '0','103' , '23' ,  , '00','01'

            bg = -1,

            idx = -1,

            idxs = [];



        // , 

        for(p in this){

            if(r.test(p)){

                idxs[i++] = parseInt(p);

            }

        }



        idxs.sort(function(idx1,idx2){

            return idx1 - idx2;

        });





        // 

        if(arguments.length >= 2){

            bg = 0;

            ret = initValue;

        }else{

            bg = 1;

            ret = this[0];

        }

        for(i=bg,l=idxs.length; i<l; i++)

        {

            idx = idxs[i];

            ret = f(ret , this[idx] , idx , this);

        }



        return ret;

    };

}

 
 
しかし、このバージョンでは効率的な問題があり、「疎配列」に対して「稠密配列」があるに違いない.稠密な配列に対しては、明らかに方法が良い.方法2の消費は、インデックス、すなわちコード内のidxsをロードするために配列の空間が必要であることだ.
3.バージョン3
以上の2つのバージョンにはそれぞれ千秋があり,稠密配列と疎配列に対してそれぞれ良し悪しがある.次は総合版をあげます.私の考えは簡単です.まず羅列します.
1)疎か判断
2)疎はfor in法,稠密はfor i現在,ある種の稠密度の配列が存在し,両方法の効率が同等になると仮定している.ニマ...数学