3
votes

Comment pousser un objet dans un tableau sans passer cet objet par référence?

J'ai donc une propriété dans une classe appelée 'tiles' qui contient des informations sur l'état d'un jeu de plateau de dames. J'essaie de pousser cette propriété vers un tableau appelé «coups» chaque fois que je fais un mouvement légal et au début de la partie. Mais le problème est que chaque fois que je pousse la nouvelle propriété tiles, les éléments précédents du tableau moves changent pour les valeurs des dernières mosaïques poussées.

Je comprends que cela se produit parce que l'objet est passé par référence et donc remplace les anciens éléments du tableau, car ils pointent maintenant vers le même objet, qui est la dernière valeur des tuiles de propriété. Donc, avec mon code ci-dessous, y a-t-il un moyen de pousser cet objet non pas par référence, mais par chaque état individuel de «tuiles» qui a résulté en raison de mouvements légaux.

Voici mon extrait: App.js

App = function () {
  var self = this;
  self.tiles = []; 
  // this is populated with objects from a json file
  //code to fetch json and save it to self.tiles
  //more code

  this.startGame = function () {
    //other code
    self.moves.push(self.tiles);
  };
  this.makeMove = function () {
    //other code
    self.moves.push(self.tiles);
  };
};

Donc, ce que j'attends du tableau self.moves, les tuiles doivent pointer vers des objets différents au lieu du même objet. Il devrait contenir différents états de self.tiles mais pour le moment, lorsque je pousse la propriété, les éléments du tableau 'moves' sont écrasés par la dernière valeur self.tiles.

Toute aide pour résoudre ce problème sera être très apprécié. Merci!


5 commentaires

la classe de tuiles implémente-t-elle le modèle .clone ()? si oui, utilisez self.moves.push (self.tiles.clone ())


Je suppose que oui, car dans le rappel, j'ai le code suivant. self.tiles = wade.cloneObject (data.data.tiles);


Hey Erch, désolé, je n'ai pas implémenté le modèle .clone () et j'étais confus au sujet de la fonction cloneObject que j'utilise et qui est livrée avec l'ES6 Game Engine. Mais la réponse de Maheer a fait l'affaire ... Mais merci quand même!


"l'objet est passé par référence" C'est une erreur courante de supposer cela, mais JavaScript est un langage pass-par-valeur. Les objets sont des valeurs de type de référence , mais ce n'est pas la même chose que le passage par référence.


Merci pour la correction Felix.


3 Réponses :


3
votes

Vous devez utiliser JSON.parse (JSON.stringify ()) pour cloner un objet imbriqué.Vous pouvez utiliser Object.assign pour cloner un objet peu profond

App = function () {
  var self = this;
  self.tiles = []; 
  // this is populated with objects from a json file
  //code to fetch json and save it to self.tiles
  //more code

  this.startGame = function () {
    //other code
    self.moves.push(JSON.parse(JSON.stringify(self.tiles)));
  };
  this.makeMove = function () {
    //other code
    self.moves.push(JSON.parse(JSON.stringify(self.tiles)));
  };
};


1 commentaires

Super merci Maheer! Ça marche comme prévu. Appréciez-le!



0
votes

La seule façon de résoudre votre problème est de transmettre le clone de l'objet que vous souhaitez insérer dans le vecteur. Dans de tels cas, vous écririez normalement une méthode clone () sur votre objet qui renvoie une copie complète de lui-même. L'objet retourné par cette méthode peut être poussé vers le tableau.


1 commentaires

Merci Ravi, le notera également.



0
votes

Je l'ai bidouillé pendant un moment et j'ai trouvé que vous pouvez utiliser l'opérateur de propagation comme ceci:

var a = {b: 1, c: 2}
var array1 = []

array1.push({...a})
a.c=3

console.log(array1) // [0: {b: 1, c: 2}]
console.log(a) // {b: 1, c: 3}

MDN: diffusion dans les littéraux d'objet


2 commentaires

Cela ne fait qu'une copie superficielle (similaire à Object .assign mais à l'exclusion du prototype). Si a était {level1: {level2: 2}} et que vous ferez ({... a}). Level1.level2 = 8 alors vous muteriez la valeur a .


donc ce que vous dites, c'est que les accessoires de l'objet "cloné" sont vraiment des références à a.prop1, a.prop2? TIL