5

MDNは、ネイティブバインドメソッドを使用しないブラウザのポリフィルバインドメソッドを指定します:https ://developer.mozilla.org/en-US/docs/JavaScript/Reference/Global_Objects/Function/bind

このコードには次の行があります。

aArgs.concat(Array.prototype.slice.call(arguments))

これは、関数のapplyメソッドに引数として渡されます。

fToBind.apply(this instanceof fNOP && oThis
                             ? this
                             : oThis,
                           aArgs.concat(Array.prototype.slice.call(arguments)));

ただし、この行は実際には引数を繰り返しているため、bindメソッドを次のように呼び出した場合:

fnX.bind({value: 666}, 1, 2, 3)

fnXに渡される引数は次のとおりです。

[1, 2, 3, Object, 1, 2, 3] 

次の例を実行して、コンソール出力http://jsfiddle.net/dtbkq/を確認します。

ただし、fnXによって報告される引数は[1、2、3]であり、これは正しいです。誰かが、apply呼び出しに渡されたときに引数が重複しているのに、関数の引数変数に表示されない理由を説明できますか?

4

3 に答える 3

4

そこargumentsには2つの異なるコンテキストがあります。特に、関数が呼び出されるたびに、arguments渡されたすべての引数にオブジェクトが設定されます(argumentsアクセスされている場合)。

の最初の言及argumentsは、への引数でbind()あり、これが最初の引数になります。

2番目の言及は、バインドされたプロキシ関数で呼び出される次の一連の引数です。arguments名前はその親arguments(およびthis分離する必要のあるコンテキスト)をシャドウするため、名前の下に格納されaArgsます。

これにより、部分機能の適用(カリー化と呼ばれることもあります)が可能になります。

var numberBases = parseInt.bind(null, "110");

console.log(numberBases(10));
console.log(numberBases(8));
console.log(numberBases(2));

jsFiddle

于 2012-10-22T00:11:38.963 に答える
1

いいえ。からログインするxと、x() arguments:です[1, 2, 3]

bind2あなたからconsole.log(aArgs.concat(Array.prototype.slice.call(arguments)));、どこでaArgs = Array.prototype.slice.call(arguments, 1)。それで、あなたは他に何[1, 2, 3, {value: 666}, 1, 2, 3]を期待しますか?これらはargumentsfnXに渡されませんが、バインドに渡されます[{value: 666}, 1, 2, 3]

バインドされた関数内では、aArgs変数にはまだが含まれていますが[1, 2, 3]arguments現在は空です-を呼び出しx()ました。

于 2012-10-22T00:13:05.297 に答える
1

aArgs.concat(Array.prototype.slice.call(arguments))代わりに、内部からの値を確認すると、fBound期待どおりの結果が得られます。重要なのは、引数がすでにバインドされている関数で呼び出される追加の引数を参照することです。

于 2012-10-22T00:13:36.860 に答える