Fonctions d'ordre supérieur en Javascript

je suis en lecture Éloquent JavaScript (La nouvelle édition) et j'ai atteint la partie sur les fonctions d'ordre supérieur et je suis confus sur ce qui se passe dans le code suivant.

function noisy(f) {
  return function(arg) {
    console.log("calling with", arg);
    var val = f(arg);
    console.log("called with", arg, "- got", val);
    return val;
  };
}
noisy(Boolean)(0);
// → calling with 0
// → called with 0 - got false
  1. Pourquoi l'appel à la fonction bruyant comme ça? Est (Boolean), un casting? Un casting pour quoi? la valeur de retour? ou de l'argument? pourquoi ne pas (Boolean)bruyant(0) si sa valeur de retour. Ou bruyant((Boolean) 0) si l'argument est un être jeter.

    noisy(Boolean)(0)
    
  2. Ce qui se passe dans cette ligne? Où f () est-il défini?

    var val = f(arg);
    
16
demandé sur Rizvi 2014-05-08 11:23:46

4 réponses

  1. Boolean est une fonction. C'est la fonction que vous appelez indirectement par noisy. Un peu confus, je sais, parce que ça ressemble au nom d'un type. Mais en JavaScript, ces choses initialement-plafonnées (Boolean,Number,String, et ainsi de suite) sont fonctions. Lorsque vous appelez Boolean (sans en utilisant new), il essaie de convertir l'argument que vous avez donné dans un boolean valeur primitive et renvoie le résultat. (Voir §15.6.1 dans la spécification.)

  2. f est le nom de l'argument dans le noisy fonction.

les fonctions en JavaScript sont des objets de première classe. Vous pouvez les transmettre à d'autres fonctions comme arguments comme tout autre objet.

Lorsque vous faites

noisy(Boolean)(0)

Il y a deux choses qui se passent. La première:

// (In effect, we're not really creating a variable...)
var x = noisy(Boolean);

cela nous donne une fonction qui, lorsqu'elle est appelée, appellera Boolean avec l'argument nous le donnons tout en faisant aussi ceux console.log consolidés. C'est la fonction que vous voyez être créée dans noisy (return function(arg)...);

alors nous appelons cette fonction:

x(0);

et c'est là que vous voyez la sortie de la console. Depuis Boolean(0)false,Boolean retour cette valeur.

voici un exemple beaucoup plus simple:

function foo(bar) {
    bar();
}
function testing() {
    alert("testing got called");
}
foo(testing);

là, je passe la fonction testing en foo. L'argument le nom que j'utilise pour en moins!--22-->bar. La ligne bar(); appelle la fonction.

19
répondu T.J. Crowder 2015-04-13 17:37:35

Une fonction sans la () est la fonction réelle. Une fonction () est un appel de la fonction. Gardez également à l'esprit que JavaScript est un langage mal dactylographié, de sorte que vous ne déclarez pas les types de variables. J'ai ajouté quelques commentaires à votre exemple pour essayer d'aider.

// We define a function named noisy that takes in an argument named f. We are expecting f to be a function but this isn't enforced till the interpreter throws an error. 
function noisy(f) {
// Noisy returns a single item, an anonymous function. That anonymous function takes in an argument named arg
  return function(arg) {
    console.log("calling with", arg);
// Our anonymous function then takes f (It can use f because its defined inside noisy, see closures for more details) and invokes it with the argument arg and stores the result in a variable named val. 
    var val = f(arg);
    console.log("called with", arg, "- got", val);
// It now returns val
    return val;
  };
}

alors bruyant(Booléenne)(0) fonctionne comme ceci

f est la fonction booléen

bruyant retourne une fonction comme ceci

function(arg) {
  var val = Boolean(arg);
  return val;
}

Alors maintenant, nous avons

notre fonction renvoyée(0)

qui s'exécute comme normal de devenir

function(0) {
  var val = Boolean(0); // false
  return val;
}
9
répondu Blue 2014-05-08 08:00:56

je suis relativement nouveau à JS et je viens aussi de lire JavaScript éloquent et j'ai trouvé plus facile à comprendre une fois que j'ai compris l'appel de la fonction (répondant à votre point 1):

noisy(Boolean)(0);

noisy(Boolean) crée une nouvelle fonction et l' (0) est après parce que c'est passé comme argument à cette nouvelle fonction. Si vous consultez le plus de exemple:

function greaterThan(n) {
  return function(m) { return m > n; };
}
var greaterThan10 = greaterThan(10);
console.log(greaterThan10(11));

on pourrait aussi l'appeler façon:

greaterThan(10)(11);

j'espère que cela clarifie votre première question sur la raison pour laquelle on l'a appelé ainsi.

Pour la deuxième question. f en:

var val = f(arg);

est le Boolean fonction qui a été passée dans noisy quand noisy(Boolean) a été saisi. Il a ensuite été utilisé comme argument dans la fonction noisy. Je ne savais pas non plus que Boolean pouvait être une fonction en soi et pas seulement un type de données. Comme d'autres l'ont dit - elle convertit l'argument que vous avez donné dans un Valeur booléenne et renvoie le résultat.

Donc val devient Boolean(arg) devient Boolean(0) qui est évalué à false. Si vous essayez d'appeler noisy(Boolean)(1);vous allez le voir de retour true. console.log("called with", arg, "- got", val); se connecte simplement l'argument (0 dans ce cas) et le résultat de l'évaluation (false).

en effet, il a changé la fonction booléenne en une qui logue l'argument et le résultat, en plus de retourner le résultat.

j'espère que cette aide. Juste pour l'écrire cela a aidé ma propre compréhension.

5
répondu Graham Schwikkard 2016-01-28 14:48:38

dans le cas où vous avez encore des problèmes avec cela, Voici comment je le comprends (il m'a donné un mal de tête aussi..)

function noisy(f) {
    return function(arg) {
        console.log("calling with", arg);
        var val = f(arg);
        console.log("called with", arg, "- got", val);
        return val;
    };
}

noisy(Boolean)(0)

une fonction est Une valeur régulièrement. La phrase précédente est la clé pour comprendre ce qui se passe ici.

notre fonction noisy (f) est une valeur. C'est de quoi il en retourne.

bruyant(f) retourne une fonction qui prend un argument (arg).

bruyant(f) prend un argument (f). Les fonctions internes (les fonctions appelées à partir à l'intérieur des fonctions) ont accès à des variables et arguments qui ont été adoptées à l'extérieur de la fonction.

nous appelons notre fonction externe et lui passons L'argument booléen. Notre fonction externe renvoie sa fonction interne qui prend un argument (0). En comprenant ce qui précède, il devrait devenir clair que noisy(Boolean (0)) passerait simplement un argument à notre fonction externe, tout en ne passant rien à la fonction intérieure qui est retournée par notre Extérieur fonction.

c'est tellement simple en fait. Maintenant que nous comprenons, il est difficile de croire qu'il nous a donné un tel mal de tête pour commencer... * / '

0
répondu Kasper Gyselinck 2017-09-13 20:17:47