2017-01-28 11 views
1

多分それは私の夜ではありません:/とても単純なこと、私は、引数配列として関数にパラメータとして配列を与えたい:引数はJavaScriptのArray(ES5)

function add() { 
    var sum = 0; 
    for (var i = 0; i < arguments.length; i++) { 
     sum += arguments[i]; 
    } 
    return sum; 
} 

次作品:

console.log(add(1,2,3,4,5,6)); 

しかし、私は、配列を埋めると同様に、パラメータとしてそれを与える場合:私は、トラブルを得る

var myNumbers = []; 
for (var i=0; i<100; i++){ 
    myNumbers.push(i); 
} 
console.log(add(myNumbers)); 

。私は、arguments配列に関して重要な何かを見逃していると思います。

両方の可能性が機能するように、どのように追加機能を変更する必要がありますか?ここで

+0

が配列であります(したがって、引数[0]としてアクセスしようとすると)追加機能 – Sai

答えて

1

add(1,2,3,4,5,6); 

... arguments[0]で1、あなたは離散(別の)一連の引数を持つaddを呼んでいる、とそれらのそれぞれはarguments擬似配列に現れ、 arguments[1]で2など

しかし、ここで:

add(myNumbers); 

..あなたはaddと呼び、という引数を配列と呼びます。それはarguments[0]です。

どのように呼び出すかに合わせて、addと書いておきます。あなたが離散引数で呼び出す場合は、あなたが持っている方法でそれを書いてください。 (

function add(args) { 
    //  ^------------- the one argument 
    var sum = 0; 
    for (var i = 0; i < args.length; i++) { 
     sum += args[i]; 
    } 
    return sum; 
} 

あなたは両方を処理したい場合は、Array.isArrayを使用することができます。あなたは、配列を受け入れるためにそれを書きたい場合は、それは(配列になります)ことによって、単一の引数とループを取るしています新しめ、それが配列だかどうかを確認するために最初の引数をチェックして、どちらかそれはあるかそうでない場合はargumentsを使用している場合はそれを使用する)shimmable:

function add(args) { 
    if (!Array.isArray(args)) { 
     args = arguments; 
    } 
    var sum = 0; 
    for (var i = 0; i < args.length; i++) { 
     sum += args[i]; 
    } 
    return sum; 
} 

サイドノート:argumentsではありませんアレイ、それはjuですst アレイ様

+0

に感謝しますあなた、どのように私は両方の作品を追加する機能を変更する必要がありますか? – Lonely

+0

@Lonely:最初の引数が['Array.isArray'](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/isArray)を介して配列であるかどうかを検出できます)(これは新機能ですが、古いブラウザでは簡単にシミングされます)。次に、最初の引数、つまり 'arguments'を使用します。私は例を追加しました。 –

2

argumentsオブジェクトは配列のようなオブジェクトですが、配列ではありません。関数に渡されたすべての引数を表すために使用されます。ある値を関数に渡しただけなので、配列は実際にargumentsオブジェクトのインデックス0になります。

ただし、明示的なAPIを定義せずに動的に処理する必要がある場合を除き、実際にはargumentsを使用している点はあまりありません。 add関数でパラメータを宣言するだけです。

function add() { 
    var arr = [].concat.apply([], arguments); 
    var sum = 0; 
    for (var i = 0; i < arr.length; i++) { 
     sum += arr[i]; 
    } 
    return sum; 
} 

説明の [].concat.apply([], arguments)

  • [].Array.prototypeの省略形です:あなたは両方のケースをサポートしたい場合は

    function add(arr) { 
        var sum = 0; 
        for (var i = 0; i < arr.length; i++) { 
         sum += arr[i]; 
        } 
        return sum; 
    } 
    

    は、あなたのコメントのとおり、あなたのような何かを行うことができますそれは空の配列だからです。

  • concatは、2つ以上の配列を一緒に、または配列と値を配列にマージします。
  • argumentsは配列ではありませんが、オブジェクトインデックス付きアイテムとlengthプロパティの配列のような特性のために、多くのプロトタイプ関数が機能します。
  • applyは、特定のコンテキスト(バインディング)と任意の数の引数を持つ関数を呼び出します。この場合は、配列thisconcatにコールし、次にすべての引数をaddに渡すことができます。結果は、単にすべての引数が適切な配列として得られます。
+0

どうもありがとうございます。どうすれば追加機能を変更すればよいのですか? – Lonely

+0

@Lonely両方のケースを扱う更新された答えを見てください。 –

+0

は 'var arr = [] .concat.apply([]、arguments);'クロスブラウザ互換? – Lonely

1

あなたは、このソリューションは、状況の両方のために働くapply

add.apply(null, [1,2,3]) 
1

を使用することができます。

function add() { 
    var arr= Array.prototype.slice.call(arguments); 
    arr = [].concat.apply([], arr); 

    var sum = 0; 
    for (var i = 0; i < arr.length; i++) { 
     sum += arr[i]; 
    } 
    return sum; 
} 

また、合計のためのシンプルなソリューション:第二ケースmyNumbersで

function add() { 
     var arr= Array.prototype.slice.call(arguments); 
     arr = [].concat.apply([], arr); 

     return arr.reduce(function(f, s){return f + s;}, 0); 
    }