Pourquoi la version est-elle une solution mais la version B ne le fait pas? Comment faire fonctionner la version B sans déclarer une variable globale en dehors de la fonction (qui est une mauvaise pratique)? Je ne sais pas pourquoi je ne peux pas simplement déclarer compter à l'intérieur de la fonction elle-même.
a) p> b) p>
5 Réponses :
La version B ne fonctionnera pas car chaque fois que la fonction est appelée code> compteur code> est redéclamé, donc compteur code> ne pas incréments. p>
Merci, ça a du sens! Une suggestion était de faire compter un paramètre. Si je fais cela, comment puis-je le gérer à l'intérieur de la fonction?
Voir @fullstacks Réponse ci-dessous sur la déclaration de valeur par défaut pour le paramètre de comptage. Ce serait la meilleure solution si vous souhaitez éviter de déclarer une variable externe.
Ce que vous avez vraiment besoin est deux fonctions em>, une à l'intérieur de l'autre: dans cette configuration, vous passez dans une référence d'élément, puis la fonction extérieure appelle la fonction interne après l'initialisation du compteur. p> Original pas très bonne réponse ici em> p> Votre deuxième version ("BE" "En tant que variable locale Si vous ne voulez pas de global, vous pouvez utiliser un Fermeture: P>
var containsFiveOrMoreDivs = function() {
var count = 0;
return function(domElement) {
if (domElement && domElement.tagName === "DIV") {
count++;
}
//base case:
if (count >= 5) {
return true;
} else {
if (domElement.hasChildNodes()) {
var children = domElement.childNodes;
for (var i = 0; i < children.length; i++) {
if (containsFiveOrMoreDivs(children[i])) {
return true;
}
}
}
return false;
}
};
}();
Votre fonction récursive doit consommer le compte comme argument. La façon dont vous l'avez initialement initialisera compter à 0, quel que soit le nombre de fois que vous recursez.
Voici un exemple de fonction récursive qui consomme "le nombre de fois à faire quelque chose" comme paramètre. Modifiez-le pour soutenir votre cas. Votre cas de base serait quelque chose comme «Compte est supérieur à 5» et chaque fois que vous appelez de manière récursive, vous ajoutez 1 au compte que vous fournissez à l'appel récursif. P>
function executeMany(fn, count) {
if (count > 0) {
fn();
executeMany(fn, count - 1)
}
}
// this logs "Test" to the console twice
executeMany(function() { console.log("Test"); }, 2);
Merci! Si je déclare compter comme un paramètre, comment le gérer à l'intérieur du corps de la fonction?
variables en JavaScript existe dans la portée de la fonction. Chaque fois que vous appelez contendefiveormoreivs, le nombre sera toujours de 0 dans votre version B. Par conséquent, une récursion infinie.
Ce que vous pouvez faire, cependant, est de passer à chaque fois que vous appelez à l'intérieur de la fonction et utilisez-le ( S'assurer qu'il est initialisé correctement la première fois): p> appelez simplement que vous êtes actuellement ( contenantfiveormoreivs ('ElementName'); p > p>
Cela ne fonctionne pas, il suffit de le tester dans la console à propos de: vide après Ajout de 5 divs! il retourne faux.
Bon point - cela fonctionnera si les DIV sont imbriquées sous l'autre, mais cela ne comptera pas les frères et sœurs! Ce problème s'applique également à la solution de @fullstack ci-dessous. @Pointy - Votre solution semble assez élégante, mais chaque fois que vous appelez contenantfiveormoreivs (enfants [i]) code> dans la fonction renvoyée, vous retournez A neuf i> B> Fermeture qui a une variable de comptage frais de la valeur 0.
Vous pouvez définir la fonction avec un paramètre code> code> et transmettre une valeur initiale ou si vous utilisez un CELMA 16, vous pouvez définir une valeur par défaut pour le paramètre en faisant compte = 0 . var containsFiveOrMoreDivs = function(domElement, count) {
if (domElement && domElement.tagName === "DIV") {
count++;
}
//base case:
if (count >= 5) {
return true;
} else {
if (domElement.hasChildNodes()) {
var children = domElement.childNodes;
for (var i = 0; i < children.length; i++) {
if (containsFiveOrMoreDivs(children[i]), count) {
return true;
}
}
}
return false;
}
};
// call function and set counter to some initial value, such as zero
containsFiveOrMoreDivs(domElement, 0);
C'était exactement ce que j'allais dire @freezycold. Grande solution.
C'est génial et cela fonctionnera dans Firefox et aucun autre navigateur actuel.
Pour ce que ça vaut la peine, votre problème n'a rien à voir avec "Pass par référence", ce qui n'est pas possible dans JavaScript de toute façon.
Y a-t-il une raison pour laquelle vous ne faites pas
élément.queryselectorall ('div'). Longueur> 5 code>?