Travailler avec des objets et des propriétés

Un objet complexe peut contenir n'importe quelle valeur JavaScript autorisée. Dans le code suivant, je crée un Objet() objet appelé monObjet puis ajoutez des propriétés représentant la majorité des valeurs disponibles en JavaScript.


Objets Complexes

Échantillon: sample29.html

 

Le concept simple à apprendre ici est que les objets complexes peuvent contenir ou faire référence à tout ce que vous pouvez nominalement exprimer en JavaScript. Cela ne devrait pas vous surprendre, car tous les objets natifs peuvent être mutés. Cela s'applique même à Chaîne(), Nombre(), et Booléen () valeurs sous leur forme d’objet, c’est-à-dire lorsqu’elles sont créées avec le Nouveau opérateur.


Encapsuler des objets complexes de manière programmatique et bénéfique

le Objet(), Tableau (), et Une fonction() les objets peuvent contenir d'autres objets complexes. Dans l'exemple suivant, je démontre ceci en configurant une arborescence d'objets à l'aide de Objet() objets.

Échantillon: sample30.html

 

La même chose peut être faite avec un Tableau () objet (ou tableau multidimensionnel), ou avec un Une fonction() objet.

Échantillon: sample31.html

 

Le concept principal à retenir ici est que certains des objets complexes sont conçus pour encapsuler d'autres objets d'une manière bénéfique par programmation..


Obtention, définition et mise à jour des propriétés d'un objet à l'aide de la notation par point ou par parenthèse

Nous pouvons obtenir, définir ou mettre à jour les propriétés d'un objet à l'aide de la notation par points ou de la notation entre crochets.

Dans l'exemple suivant, je démontre la notation par points, qui est réalisée en utilisant le nom d'objet suivi d'un point, puis de la propriété pour obtenir, définir ou mettre à jour (par exemple,., objectName.property).

Échantillon: sample32.html

 

La notation par points est la notation la plus courante pour obtenir, définir ou mettre à jour les propriétés d'un objet..

La notation de support, à moins que cela ne soit requis, n’est pas aussi couramment utilisée. Dans l'exemple suivant, je remplace la notation par points utilisée dans l'exemple précédent par la notation entre crochets. Le nom de l'objet est suivi d'un crochet ouvrant, du nom de la propriété (entre guillemets), puis d'un crochet fermant:

Échantillon: sample33.html

 

La notation entre crochets peut être très utile lorsque vous devez accéder à une clé de propriété et que vous devez travailler avec une variable qui contient une valeur de chaîne représentant le nom de la propriété. Dans l'exemple suivant, je démontre l'avantage de la notation entre crochets par rapport à la notation point en l'utilisant pour accéder à la propriété foobar. Je le fais en utilisant deux variables qui, une fois jointes, produisent la version chaîne de la clé de propriété contenue dans foobarObject.

Échantillon: sample34.html

 

De plus, la notation entre crochets peut s'avérer utile pour obtenir des noms de propriété qui sont des identificateurs JavaScript non valides. Dans le code suivant, j'utilise un nombre et un mot clé réservé comme nom de propriété (valide en tant que chaîne) auquel seule la notation entre crochets peut accéder..

Échantillon: sample35.html

 

Parce que les objets peuvent contenir d'autres objets, cody.object.object.object.object ou cody ['objet'] ['objet'] ['objet'] ['objet'] peut être vu parfois. Ceci est appelé chaînage d'objets. L'encapsulation d'objets peut durer indéfiniment.

Les objets sont modifiables en JavaScript, ce qui signifie que leur obtention, leur définition ou leur mise à jour peut être effectuée à tout moment sur la plupart des objets. En utilisant la notation entre crochets (par exemple., cody ['age']), vous pouvez imiter des tableaux associatifs trouvés dans d’autres langues.

Si une propriété à l'intérieur d'un objet est une méthode, il suffit d'utiliser le () opérateurs (par exemple., cody.getGender ()) pour invoquer la méthode property.


Suppression des propriétés d'un objet

le effacer L'opérateur peut être utilisé pour supprimer complètement les propriétés d'un objet. Dans l'extrait de code suivant, nous supprimons le bar propriété de la foo objet.

Échantillon: sample36.html

 

effacer ne supprimera pas les propriétés trouvées sur la chaîne de prototypes.

La suppression est le seul moyen de supprimer une propriété d'un objet. Définir une propriété sur indéfini ou nul ne modifie que la valeur de la propriété. Il ne supprime pas la propriété de l'objet.


Comment les références aux propriétés d'objet sont résolues

Si vous essayez d'accéder à une propriété qui n'est pas contenue dans un objet, JavaScript tentera de trouver la propriété ou la méthode à l'aide de la chaîne de prototypes. Dans l'exemple suivant, je crée un tableau et tente d'accéder à une propriété appelée foo cela n'a pas encore été défini. Vous pourriez penser que parce que myArray.foo n'est pas une propriété du mon tableau objet, JavaScript reviendra immédiatement indéfini. Mais JavaScript va chercher dans deux autres endroits (Array.prototype et alors Object.prototype) pour la valeur de foo avant qu'il ne revienne indéfini.

Échantillon: sample37.html

 

la propriété. S'il possède la propriété, il retournera la valeur de la propriété et aucun héritage ne se produira car la chaîne de prototypes n'est pas exploitée. Si l'instance ne possède pas la propriété, JavaScript la recherchera ensuite dans la fonction constructeur de l'objet. prototype objet.

Toutes les instances d’objet ont une propriété qui est un lien secret __proto__) à la fonction constructeur qui a créé l’instance. Ce lien secret peut être exploité pour saisir la fonction constructeur, en particulier la propriété prototype de la fonction constructeur d'instances..

C'est l'un des aspects les plus déroutants des objets en JavaScript. Mais raisonnons cela. Rappelez-vous qu'une fonction est aussi un objet avec des propriétés. Il est logique d'autoriser les objets à hériter des propriétés d'autres objets. Juste comme dire: "Hey objet B, je voudrais que vous partagiez toutes les propriétés de cet objet A." JavaScript fils tout cela pour les objets natifs par défaut via le prototype objet. Lorsque vous créez vos propres fonctions de constructeur, vous pouvez également utiliser le chaînage de prototypes..

Comment exactement JavaScript accomplit ceci est déroutant jusqu'à ce que vous le voyiez tel qu'il est: juste un ensemble de règles. Créons un tableau pour examiner la prototype propriété plus proche.

Échantillon: sample38.html

 

Notre Tableau () instance est un objet avec des propriétés et des méthodes. Lorsque nous accédons à l’une des méthodes de tableau, telles que joindre(), demandons-nous: l'instance myArray créée à partir du Tableau () le constructeur a son propre joindre() méthode? Allons vérifier.

Échantillon: sample39.html

 

Non. MyArray a pourtant accès au joindre() méthode comme si elle était sa propre propriété. Que s'est-il passé ici? Eh bien, vous venez d’observer la chaîne de prototypes en action. Nous avons accédé à une propriété qui, bien que ne figurant pas dans l'objet myArray, puisse être trouvée par JavaScript ailleurs. Cet endroit est très spécifique. Quand le Tableau () constructeur a été créé par JavaScript, le joindre() la méthode a été ajoutée (entre autres) comme une propriété de prototype propriété de Tableau ().

Pour réitérer, si vous essayez d'accéder à une propriété sur un objet qui ne la contient pas, JavaScript recherchera prototype chaîne pour cette valeur. Il s’agira d’abord de la fonction constructeur qui a créé l’objet (par exemple,., Tableau) et inspecter son prototype (par exemple., Array.prototype) pour voir si la propriété peut être trouvée là. Si le premier objet prototype ne possède pas la propriété, JavaScript continue de chercher dans la chaîne jusqu'au constructeur situé derrière le constructeur initial. Il peut faire cela jusqu'au bout de la chaîne.

Où finit la chaîne? Examinons à nouveau l'exemple, en invoquant le toLocaleString () méthode sur mon tableau.

Échantillon: sample40.html

 

le toLocaleString () méthode n'est pas définie dans le mon tableau objet. Ainsi, la règle de chaînage prototype est invoquée et JavaScript recherche la propriété dans la Tableau constructeurs prototype propriété (par exemple., Array.prototype). Elle n’y figure pas non plus. La règle de chaîne est à nouveau invoquée et nous recherchons la propriété dans la liste. Objet() propriété du prototype (Object.prototype). Et oui, il se trouve là. Si JavaScript n’avait pas été trouvé, JavaScript aurait produit une erreur indiquant que la propriété était indéfini.

Toutes les propriétés du prototype étant des objets, le dernier maillon de la chaîne est Object.prototype. Aucune autre propriété de prototype de constructeur ne peut être examinée..

Il y a tout un chapitre à venir qui décompose la chaîne de prototypes en parties plus petites. Si cela vous a complètement échappé, lisez-le, puis revenez à cette explication pour renforcer votre compréhension. J'espère que de cette brève lecture, vous comprendrez que lorsqu'une propriété n'est pas trouvée (et réputée indéfini), JavaScript aura examiné plusieurs objets prototypes pour déterminer qu’une propriété est indéfini. Une recherche a toujours lieu, et ce processus de recherche explique comment JavaScript gère l'héritage ainsi que les recherches de propriétés simples..


En utilisant hasOwnProperty vérifier qu'une propriété d'objet ne fait pas partie de la chaîne de prototypes

Tandis que le dans L’opérateur peut vérifier les propriétés d’un objet, y compris celles de la chaîne de prototypes, hasOwnProperty La méthode peut vérifier un objet pour une propriété qui ne provient pas de la chaîne de prototypes.

Dans l'exemple suivant, nous voulons savoir si monObjet contient la propriété foo, et qu'il n'hérite pas de la propriété de la chaîne de prototypes. Pour ce faire, nous demandons si monObjet a sa propre propriété appelée foo.

Échantillon: sample41.html

 

le hasOwnProperty La méthode doit être exploitée lorsque vous devez déterminer si une propriété est locale à un objet ou héritée de la chaîne de prototypes..


Vérifier si un objet contient une propriété donnée en utilisant le dans Opérateur

le dans L'opérateur est utilisé pour vérifier (vrai ou faux) si un objet contient une propriété donnée. Dans cet exemple, nous vérifions si foo est une propriété en monObjet.

Échantillon: sample42.html

 

Vous devriez être conscient que le dans L’opérateur vérifie non seulement les propriétés contenues dans l’objet référencé, mais également toutes les propriétés dont cet objet hérite via prototype chaîne. Ainsi, les mêmes règles de recherche de propriété s'appliquent et la propriété, si elle ne figure pas dans l'objet actuel, sera recherchée sur le prototype chaîne.

Cela signifie que myObject de l'exemple précédent contient en fait un toString méthode de propriété via le prototype chaîne (Object.prototype.toString), même si nous n’en avons pas spécifié un (par exemple., myObject.toString = 'foo').

Échantillon: sample43.html

 

Dans le dernier exemple de code, la propriété toString ne se trouve pas littéralement à l'intérieur de l'objet myObject. Cependant, il est hérité de Object.prototype, et donc le dans l'opérateur conclut que monObjet a en fait un hérité toString () méthode de la propriété.


Énumérer (boucler) les propriétés d'un objet à l'aide de pour dans Boucle

En utilisant pour dans, nous pouvons faire une boucle sur chaque propriété d'un objet. Dans l'exemple suivant, nous utilisons le pour dans boucle pour récupérer les noms de propriété de l'objet cody.

Échantillon: sample44.html

 

le pour dans La boucle a un inconvénient. Il n’accédera pas uniquement aux propriétés de l’objet en cours de bouclage. Il inclura également dans la boucle les propriétés héritées (via la chaîne de prototypes) par l'objet. Ainsi, si ce n’est pas le résultat souhaité et si ce n’est pas le cas, nous devons utiliser un simple si déclaration à l'intérieur de la boucle pour vous assurer que nous n'accédons qu'aux propriétés contenues dans l'objet spécifique sur lequel nous effectuons une boucle. Cela peut être fait en utilisant le hasOwnProperty () méthode héritée par tous les objets.

L'ordre dans lequel les propriétés sont accédées dans la boucle n'est pas toujours l'ordre dans lequel elles sont définies dans la boucle. En outre, l'ordre dans lequel vous avez défini les propriétés n'est pas nécessairement l'ordre dans lequel elles sont consultées..

Seules les propriétés énumérables (c'est-à-dire disponibles lors d'une boucle sur les propriétés d'un objet) s'affichent avec pour dans boucle. Par exemple, la propriété constructeur n'apparaîtra pas. Il est possible de vérifier quelles propriétés sont énumérables avec le propertyIsEnumerable () méthode.


Objets hôtes et objets natifs

Sachez que l'environnement (navigateur Web, par exemple) dans lequel JavaScript est exécuté contient généralement ce que l'on appelle des objets hôtes. Les objets hôtes ne font pas partie de l'implémentation ECMAScript, mais sont disponibles en tant qu'objets lors de l'exécution. Bien entendu, la disponibilité et le comportement d’un objet hôte dépendent entièrement de ce que l’environnement hôte fournit..

Par exemple, dans l’environnement du navigateur Web, l’objet window / head et tous les objets qu’il contient (à l’exception de ce que JavaScript fournit) sont considérés comme des objets hôtes..

Dans l'exemple suivant, j'examine les propriétés du la fenêtre objet.

Échantillon: sample45.html

 

Vous avez peut-être remarqué que les objets JavaScript natifs ne sont pas répertoriés parmi les objets hôtes. Il est assez courant qu'un navigateur fasse la distinction entre les objets hôtes et les objets natifs.

En ce qui concerne les navigateurs Web, le plus célèbre de tous les objets hébergés est l'interface de travail avec les documents HTML, également appelée DOM. L’exemple suivant est une méthode permettant de répertorier tous les objets contenus dans le window.document objet fourni par l'environnement du navigateur.

Échantillon: sample46.html

 

Ce que je veux que vous appreniez ici, c'est que la spécification JavaScript ne concerne pas les objets hôtes et inversement. Il existe une ligne de démarcation entre ce que JavaScript fournit (par exemple, JavaScript 1.5, ECMA-262, Édition 3 et JavaScript 1.6, 1.7, 1.8, 1.8.1, 1.8.5 de Mozilla) et ce que l'environnement hôte fournit être confus.

L’environnement hôte (navigateur Web, par exemple) qui exécute du code JavaScript fournit généralement l’objet tête (objet fenêtre, par exemple, dans un navigateur Web), où les parties natives du langage sont stockées avec les objets hôtes (par exemple,., window.location dans un navigateur Web) et des objets définis par l'utilisateur (par exemple, le code que vous écrivez pour s'exécuter dans le navigateur Web).

Parfois, un fabricant de navigateur Web, en tant qu'hôte de l'interpréteur JavaScript, fait avancer une version de JavaScript ou ajoute des spécifications futures à JavaScript avant leur approbation (par exemple, Firefox JavaScript 1.6, 1.7, 1.8, 1.8.1, 1.8 de Mozilla. 5).


Amélioration et extension d'objets avec Underscore.js

JavaScript 1.5 manque quand vient le temps de manipuler et de gérer sérieusement les objets. Si vous utilisez JavaScript dans un navigateur Web, j'aimerais être audacieux et suggérer l'utilisation de Underscore.js lorsque vous avez besoin de davantage de fonctionnalités que celles fournies par JavaScript 1.5. Underscore.js fournit les fonctionnalités suivantes pour traiter des objets.

Ces fonctions fonctionnent sur tous les objets et tableaux:

  • chaque()
  • carte()
  • réduire()
  • réduireDroit ()
  • détecter()
  • sélectionner()
  • rejeter()
  • tout()
  • tout()
  • comprendre()
  • invoquer()
  • cueillir()
  • max ()
  • min ()
  • Trier par()
  • sortIndex ()
  • toArray ()
  • Taille()

Ces fonctions fonctionnent sur tous les objets:

  • clés()
  • valeurs()
  • les fonctions()
  • étendre()
  • cloner()
  • robinet()
  • est égal()
  • est vide()
  • isElement ()
  • isArray ()
  • isArguments
  • isFunction ()
  • isString ()
  • isNumber
  • isBoolean
  • isDate
  • isRegExp
  • isNaN
  • isNull
  • isUndefined

Conclusion

J'aime cette bibliothèque car elle tire parti des nouveaux ajouts natifs à JavaScript pris en charge par les navigateurs, mais offre également les mêmes fonctionnalités aux navigateurs qui ne le font pas, le tout sans modifier l'implémentation native de JavaScript sauf si cela est nécessaire..

Avant de commencer à utiliser Underscore.js, assurez-vous que les fonctionnalités dont vous avez besoin ne sont pas déjà fournies par une bibliothèque ou une structure JavaScript qui est peut-être déjà utilisée dans votre code..