Olá pessoal. Tudo certo?!
No post anterior, mostrei como aplicar alguns princípios fundamentais (map e reduce) de programação funcional em JavaScript. Hoje, mostrocomo implementar Higher-order functions.
Live demo: http://users.cjb.net/livedemoelemarjr/higherorderfunctions.htm
Gist: https://gist.github.com/1363062
Uma “higher-order function” recebe uma ou mais funções como parâmetro e devolve uma nova função como retorno.
Comecemos a explicar os conceitos com um exemplo muito simples. Considere os testes abaixo:
test("isOdd/isEven", function () {
ok(!isOdd(2), "isOdd, passing 2, returns false.");
ok(isEven(2), "isEven, passing 2, returns true.");
});
Como você pode perceber, defini duas funçõesp para testar “par e impar”. Abaixo, está minha implementação:
var isEven = function (input) {
return input % 2 === 0;
}
var not = function (f) {
return function () {
return !f.apply(this, arguments);
};
}
var isOdd = not(isEven);
Reparem a forma pouco ortodoxa que implementamos a função isOdd. A função not é uma higher-order function (recebe e devolve uma função). Pegou a idéia?!
Agora que já vimos um exemplo, de alto nível, vamos a algo um pouco mais elaborado. Comecemos com nosso teste:
test("isNegative/isZero/isPositive", function () {
ok(isNegative(-1), "isNegative, passing -1, returns true.");
ok(!isNegative(0), "isNegative, passing 0, returns false.");
ok(!isNegative(1), "isNegative, passing 1, returns false.");
});
Agora, a implementação:
var isPositive = function (input) {
return input > 0;
};
var isZero = function (input) { return input === 0; };
var and = function (f, g) {
return function () {
return f.apply(this, arguments) &&
g.apply(this, arguments);
};
};
var isNegative = and(not(isPositive), not(isZero));
A função and também é uma higher-order function.
Considere o código abaixo:
var square = function (input) { return input * input };
var sum = function (a, b) { return a + b };
var compose = function (f, g) {
return function () {
return f.call(this, g.apply(this, arguments));
};
};
var squareOfSum = compose(square, sum);
As funções square e sum executam operações muito simples. squareOfSum combina as duas funções. Veja o teste:
test("composing", function () {
equals(squareOfSum(6, 3), 81, "squareOfSum, passing 6 and 3, returns 81.");
});
Para terminar, um exemplo que combina o post anterior com o post de hoje. Considere:
var mapper = function (f) {
return function (a) { return map(a, f); };
};
var incrementer = mapper(function (input) { return input + 1 });
Entendeu o que fizemos aqui?! Então entendeu os posts.
![]()
Testes: