10

次のコードは機能します。機能する理由は理解していますが、どこにも見たことがありません。これは、他のすべての設計パターンがはるかに優れているためだと思います。

私はまだ、この例が注意喚起の物語であると期待していましたが、そうではありませんでした。

確かに、それはひどいものです。特に、それが何をするかが明確であるため、私が選んだ以下の例では:

このパターンは何と呼ばれていますか?

一般的に使用されていますか?

このパターンを使用する正当なプロジェクトはありますか?

var add = function container (val) {

  addFunc = function f (val, undefined) {
  addFunc.total += val;
  return addFunc;
  };

addFunc.total = 0;

return addFunc(val);
};

alert(add(1)(2)(3).total);
alert(add(1)(2)(33).total);

編集: コードが IE で機能するように変数名を変更します。

4

4 に答える 4

4

技術的には、これは連鎖またはカプセル化と見なすことができます。

元の関数から無期限に一連の操作を実行できる場合は、チェーンします。jQueryは、呼び出しをチェーンして元のセレクターからプロパティと属性を設定できる場合に、この形式を使用します。この状況では、作成者は、関数名を再入力しなくても、呼び出しをチェーンして追加できるようにしたいと考えていました。最もクリーンなアイデアではありませんが、有効です。

また、コードの実際の本体が呼び出し元に公開されることaddFuncはないため、メソッドが外部スコープに公開されないため、これもカプセル化と見なすことができます。

于 2012-04-17T15:54:37.143 に答える
4

これは、カリー化 と呼ばれる関数型プログラミングの概念です。

基本的に、与えられた afunction foo(a, b, c)を作成し、function bar(a)それが返され、それが最終的な答えをfunction bar2(b)返します。function bar3(c)

技術的には、これは真のカリー化ではありません。これは、無限に続き、副作用 (totalプロパティ) を使用して無限ループから抜け出すためです。

しかし、いずれにせよ、このパターンの有用なアプリケーションが存在する可能性があります。これは、結果がその葉の祖先に依存するツリーの各葉の結果を計算しているツリー構造をトラバースする場合に特に役立ちます。ルート ノードでカリー化された関数を実行してから、返された関数を各子ノードで実行し、次にそれらの子ノードごとに実行します。純粋なカリー化された関数は、実行中のノードに子がある場合、別の関数を返します。葉に到達した場合は、目的の値を返します。

コードは、新しい「ルート」ノードとそれを解析する関数を自分自身に渡す単純な再帰関数であり、常に 1 つの引数を取ります。

しかし、ここで使われている方法は、役に立つものというよりは、学習演習のように見えます。

編集: 純粋なカリー化関数にしたいが準無限再帰が必要な場合、入力データは停止情報を提供する必要があります (C 文字列が値を使用して0x00を定義するようにEOF):

var add = (function() {
    var total = 0;
    return function nextAdd(a) {
        if(a != null) {
            total += a;
            return nextAdd;
        } else {
            return total;
        }
    };
})();

次に、副作用パラメーターadd(1)(2)(3)(null) === 6はありません。.total

于 2012-04-17T16:17:16.690 に答える
1

あなたは次のことで無限に良くなるでしょう:

function add() {
    var l = arguments.length, i, sum = 0;
    for( i=0; i<l; i++) sum += arguments[i];
    return sum;
}
alert(add(1,2,3)); // 6

本当に、あなたが求めているコードスタイルの理由はないはずです。私は合法的な使用を見たことがなく、任意のarguments長さしか見ていません。

于 2012-04-17T15:54:51.060 に答える
1

これは Currying wikipediaと呼ばれます。Haskell Curry wikipediaの名前に由来します(ただし、もともとは Moses Ilyich Schönfinkel wikipediaによって開発されました)。

複数の引数 (または n タプルの引数) を取る関数を、それぞれが 1 つの引数を持つ一連の関数として呼び出せるように変換する手法 (部分適用)。

2010 年のJavaScript パターンから:

カリー化を使用する場合 - 同じ関数を呼び出し、ほとんど同じパラメーターを渡すことに気付いた場合、その関数はおそらくカリー化の適切な候補です。関数に一連の引数を部分的に適用することで、新しい関数を動的に作成できます。新しい関数は、繰り返されるパラメーターを保存しておき (そのため、毎回パラメーターを渡す必要はありません)、それらを使用して、元の関数が期待する引数の完全なリストを事前に入力します。

ダスティン・ディアスによるカリー化に関する別の記事。

于 2012-04-17T16:13:43.020 に答える