En JavaScript, nous avons plusieurs façons d'obtenir les propriétés d'un objet, en fonction de ce que nous voulons obtenir.
1) Object.keys()
, qui renvoie toutes les propriétés propres et énumérables d'un objet, une méthode ECMA5.
2) un for...in
boucle, qui renvoie toutes les propriétés énumérables d'un objet, qu'elles soient propres ou héritées de la chaîne de prototypes.
3) Object.getOwnPropertyNames(obj)
qui renvoie toutes les propriétés propres d'un objet, énumérables ou non.
Nous avons également des méthodes qui hasOwnProperty(prop)
nous permettent de vérifier si une propriété est héritée ou appartient réellement à cet objet, et propertyIsEnumerable(prop)
qui, comme son nom l'indique, nous permet de vérifier si une propriété est énumérable.
Avec toutes ces options, il n'y a aucun moyen d'obtenir un propriété non énumérable et non propre d'un objet, ce que je veux faire. Y a-t-il un moyen de faire ça? En d'autres termes, puis-je obtenir d'une manière ou d'une autre une liste des propriétés non énumérables héritées?
Je vous remercie.
la source
Réponses:
Puisque vous
getOwnPropertyNames
pouvez obtenir des propriétés non énumérables, vous pouvez les utiliser et les combiner avec la progression de la chaîne de prototypes.Je l'ai testé sur Safari 5.1 et j'ai obtenu
Mise à jour: refactorisation un peu du code (ajout d'espaces et d'accolades et amélioration du nom de la fonction):
la source
while(curr = Object.getPrototypeOf(cure))
comme l'instruction conditionnelle utilise un opérateur d'affectation au lieu d'un opérateur de comparaison, cela ne retournerait-il pas toujours vrai? Ou est-ce que cette ligne vérifie essentiellement si "curr" a un prototype?Object.getPrototypeOf(cure)
retournull
en haut de la chaîne de prototypes. Je suppose que cela ne suppose aucune chaîne prototype circulaire!Function.prototype
ne peut jamais être le prototype «racine», puisque son lien prototype pointe versObject.prototype
. La fonctionObject.getPrototypeOf( obj )
renvoie l'objet le plus haut de la chaîne de prototypes deobj
. Il vous permet de suivre la chaîne de prototypesobj
jusqu'à ce que vous atteigniez sa fin (lanull
valeur). Je ne sais pas quel est votre problème avec ceci ...undefined
.Object.getPrototypeOf(John)
renvoie l'Boy.prototype
objet (comme il se doit) - voir ici: jsfiddle.net/aeGLA/1 . Notez que le constructeurBoy
n'est pas dans la chaîne de prototypes deJohn
. La chaîne prototypeJohn
est la suivante:Boy.prototype -> Object.prototype -> null
.John
, son constructeur estBoy
et laprototype
propriété deBoy
estBoy.prototype
. DoncObject.getPrototypeOf(John)
revientBoy.prototype
.Une solution plus propre utilisant la récursivité:
Éditer
Fonctions plus génériques:
Ce même modèle peut être appliqué en utilisant
Object.getOwnPropertySymbols
, etc.la source
Profiter des sets conduit à une solution un peu plus propre, l'OMI.
la source
Itératif simple dans ES6:
Exemple d'exécution:
Afficher l'extrait de code
la source
Pour obtenir toutes les propriétés ou méthodes héritées d'une instance, vous pouvez utiliser quelque chose comme ça
la source
Object.getInherited
plutôt queObject.prototype.getInherited
. Faire cela supprime également le besoin de la vilaine!(name == 'getInherited')
chèque. De plus, dans votre implémentation, leprops
tableau peut contenir des propriétés en double. Enfin, quel est le but d'ignorer laconstructor
propriété?Voici la solution que j'ai trouvée en étudiant le sujet. Pour obtenir toutes les propriétés non propres non énumérables de l'
obj
objet, faitesgetProperties(obj, "nonown", "nonenum");
la source
Exemple d'utilisation:
la source
si vous essayez de consigner les propriétés non énumérables d'un objet parent ex. par défaut, les méthodes définies dans une classe dans es6 sont définies sur prototype mais sont définies comme non énumérables.
la source
Une implémentation dans mes préférences personnelles :)
la source