Как я могу передать ссылку на функцию с параметрами?[дубликат]

StackOverflow https://stackoverflow.com/questions/373157

Вопрос

Возможный Дубликат:
Как я могу предварительно задать аргументы при вызове функции JavaScript?(Частичное применение функции)

Мне нужно уметь передайте ссылку на функцию с заданным набором параметров.

Вот пример передачи ссылки без параметры:

var f = function () {
    //Some logic here...
};

var fr = f; //Here I am passing a reference to function 'f', without parameters
fr(); //the 'f' function is invoked, without parameters

Теперь, что мне нужно сделать, это передать то же самое f функция, но на этот раз мне нужно было бы передать параметры ссылке.Теперь я могу сделать это с помощью анонимной функции и вызвать f функция с параметрами внутри вновь созданной функции, например, такая:

var f = function () {
        //Some logic here...
    };

var fr = function (pars) {
    f(pars);
}; //Here I am creating an anonymous function, and invoking f inside it

fr({p : 'a parameter'}); //Invoking the fr function, that will later invoke the f function with parameters

Но мой вопрос заключается в следующем, Есть ли способ передать прямую ссылку на f функция С параметрами для fr, но без включения его в анонимную функцию?

Что мне нужно назначить для fr чтобы сделать его вызываемым без параметров (fr()), так что f(1,2,3) выполняется, когда fr вызывается?

[ОБНОВЛЕНИЕ] Я последовал за ним Джейсон Бантингответ на здесь о том , что Частичная Функция и функция JavaScript, которую он там публикует, - это именно то, что я искал.Вот решение:

function partial(func /*, 0..n args */) {
  var args = Array.prototype.slice.call(arguments).splice(1);
  return function() {
    var allArguments = args.concat(Array.prototype.slice.call(arguments));
    return func.apply(this, allArguments);
  };
}
Это было полезно?

Решение

То, к чему вы стремитесь, называется частичное применение функции.

Пусть вас не вводят в заблуждение те, кто не понимает тонкой разницы между этим и приготовлением карри, они являются другой.

Приложение с частичной функцией может быть использовано для реализации, но не является приготовление карри.Вот цитата из сообщение в блоге о разнице:

Там, где частичное приложение принимает функцию и из нее создает функцию, которая принимает меньше аргументов, currying создает функции, которые принимают несколько аргументов, путем составления функций, каждая из которых принимает один аргумент.

На этот вопрос уже был дан ответ, смотрите этот вопрос для вашего ответа: Как я могу предварительно задать аргументы при вызове функции JavaScript?

Пример:

var fr = partial(f, 1, 2, 3);

// now, when you invoke fr() it will invoke f(1,2,3)
fr();

Опять же, смотрите этот вопрос для получения подробной информации.

Другие советы

Вы также можете перегрузить прототип функции:

// partially applies the specified arguments to a function, returning a new function
Function.prototype.curry = function( ) {
    var func = this;
    var slice = Array.prototype.slice;
    var appliedArgs = slice.call( arguments, 0 );

    return function( ) {
        var leftoverArgs = slice.call( arguments, 0 );
        return func.apply( this, appliedArgs.concat( leftoverArgs ) );
    };
};

// can do other fancy things:

// flips the first two arguments of a function
Function.prototype.flip = function( ) {
    var func = this;
    return function( ) {
        var first = arguments[0];
        var second = arguments[1];
        var rest = Array.prototype.slice.call( arguments, 2 );
        var newArgs = [second, first].concat( rest );

        return func.apply( this, newArgs );
    };
};

/*
e.g.

var foo = function( a, b, c, d ) { console.log( a, b, c, d ); }
var iAmA = foo.curry( "I", "am", "a" );
iAmA( "Donkey" );
-> I am a Donkey

var bah = foo.flip( );
bah( 1, 2, 3, 4 );
-> 2 1 3 4
*/

Следующее эквивалентно вашему второму блоку кода:

var f = function () {
        //Some logic here...
    };

var fr = f;

fr(pars);

Если вы хотите на самом деле передать ссылку на функцию какой-либо другой функции, вы можете сделать что-то вроде этого:

function fiz(x, y, z) {
    return x + y + z;
}

// elsewhere...

function foo(fn, p, q, r) {
    return function () {
        return fn(p, q, r);
    }
}

// finally...

f = foo(fiz, 1, 2, 3);
f(); // returns 6

Тем не менее, вам почти наверняка лучше использовать фреймворк для такого рода вещей.

Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top