2016-10-10 23 views
5

Surfowałem tu przez jakiś czas i nadal nie znalazłem odpowiedzi, która zadziałałaby dla mnie.Jak głęboko skopiować niestandardowy obiekt w JavaScript?

Czy istnieje sposób na głębokie skopiowanie niepustego obiektu w JS?

Próbowałem już jQuery.extend(true, {}, this), ale sklonował tylko niektóre z nich, reszta pozostała jako odniesienie do innego obiektu.

+1

_ „ale to tylko sklonowane niektóre z nich, reszta pozostała jako odniesienie do innego obiektu.” _ Czy to obiekt znajdujący się w pytaniu, tworzyć stacksnippets wykazać? – guest271314

+0

Zawsze jest hack "JSON.parse (JSON.stringify (...))". –

+1

@AkshatMahajanJeśli jest to format JSON, to dobrze, OP podpowiada, że ​​ma funkcje. – epascarello

Odpowiedz

4

Można użyć cloneDeep funkcję lodash za - https://lodash.com/docs/4.16.4#cloneDeep

Przykład (od docs)

var objects = [{ 'a': 1 }, { 'b': 2 }]; 

var deep = _.cloneDeep(objects); 
console.log(deep[0] === objects[0]); 
// => false 
7

Jeśli obiekt nie posiada żadnych okrągłych referencje lub funkcje jak wartości, można użyć json stringify sztuczki :

let myCopy = JSON.parse(JSON.stringify(myObject)); 

Nie wymaga żadnych bibliotek i działa bardzo dobrze w przypadku większości obiektów.

+0

Czy ta kopia będzie działać w 'myObject'? – guest271314

+1

@ guest271314 Nie. Ale dlaczego dodajesz funkcje do struktur danych? Funkcje muszą być rutynowe w innym miejscu. To jest po prostu błąd OOP)) – Deep

+0

@Deep Przykładem obiektu mającego właściwości, w których funkcje są ustawione jako wartości, byłaby funkcja 'document' lub' window' – guest271314

0

Jeśli masz do czynienia z instancją klasy, możesz użyć czegoś takiego.

Nie trzeba kopiować funkcji, do których są delegowane na prototypie.

// myObject constructor 
 
function myObject(foo, bar){ 
 
    this.foo = foo 
 
    this.bar = bar 
 
} 
 
// delegate the functions to a prototype 
 
myObject.prototype.something = function(){ 
 
    console.log('something') 
 
} 
 

 
function instanceCopy(obj) { 
 
    // copy the object by the constructor 
 
    const copy = new obj.constructor() 
 
    const keys = Object.keys(obj) 
 
    keys.forEach(key => { 
 
    copy[key] = obj[key] 
 
    }) 
 
    return copy 
 
} 
 

 
const myObj = new myObject('foo', 'bar') 
 
const copyObj = instanceCopy(myObj) 
 

 
console.log('myObj', myObj) 
 
console.log('copyObj', copyObj) 
 
console.log('same ?', copyObj === myObj) 
 

 
// can we still call the functions 
 
copyObj.something()
<script src="https://codepen.io/synthet1c/pen/WrQapG.js"></script>