Heim > Artikel > Web-Frontend > Eingehende Analyse von Objektkopiermethoden in JavaScript (mit Code)
Im vorherigen Artikel „Was Sie über die Verwendung von JavaScript „jquery inheritance“ wissen müssen (detaillierte Code-Erklärung) “ haben wir etwas über die Verwendung von JavaScript „jquery inheritance“ gelernt. Der folgende Artikel stellt Ihnen die Methode zum Kopieren von Objekten in JS vor. Freunde in Not können sich darauf beziehen.
Apropos Objektkopieren in javascript
: Das erste, woran wir denken, ist Object.assign()
javascript
中的对象拷贝,首先我们想到的是Object.assign()
JSON.parse(JSON.stringify()),
还有ES6
的展开操作符[...
]
因为在js
中=
运算符 对于对象来说,不能创建副本,只是对该对象的引用
var x = { a: 1, b: 2, }; y = x; x.a = 10; console.log(x); //{a:10, b:2} console.log(y); //{a:10, b:2}
所以在进行对象操作时,运算符等于号(=
)不可取
var x = { a: 1, b: 2, }; y = Object.assign({}, x); x.a = 10; console.log(x); //{a:10, b:2} console.log(y); //{a:1, b:2}
初看,不会发现异常,因为所要的就是我们所要的结果,把对象结构弄再稍微复杂些再看
var x = { a: 1, b: 2, c: { d: 3, }, }; y = Object.assign({}, x); x.a = 5; console.log(x); //{a:5, b:2, c:{d:3}} console.log(y); //{a:5, b:2, c:{d:3}} x.c.d = 10; console.log(x); //{a:5, b:2, c:{d:10}} console.log(y); //{a:5, b:2, c:{d:10}}
此时就发现坑了,那么已经证明了Object.assign()
只是实现了对象的浅拷贝
Object.assign()
还需要注意的一点是,原型链上属性的不可枚举对象是无法复制的,看一下代码:
var x = { a: 1, }; var y = Object.create(x, { b: { value: 2, }, c: { value: 3, enumerable: true, }, }); var z = Object.assign({}, y); console.log(z); //{c:3}
拿到z
的值很让人意外,因为x
是y
的原型链,所以x
不会被复制
属性b
是不可枚举属性,也不会被复制
只有c
具有可枚举描述,他可以被枚举,所以才能被复制
以上的坑也可以很好的被解决,且往下看:
JSON.parse(JSON.stringify())
解决浅拷贝的坑
var x = { a: 1, b: 2, c: { d: 3, }, }; y = JSON.parse(JSON.stringify(x)); x.a = 5; x.c.d = 10; console.log(x); //{a:5, b:2, c:{d:10}} console.log(y); //{a:1, b:2, c:{d:3}}
当然普通的对象,此种复制方式已经是基本是完美了,那么他的坑在哪里呢
var x = { a: 1, b: function b() { return "2"; }, }; y = JSON.parse(JSON.stringify(x)); z = Object.assign({}, x); console.log(y); //{a:1} console.log(z); //{a:1, b:function b(){return '2'}}
从结果看来,Object.assign()
可以复制方法,JSON.parse(JSON.stringify())
不可以
再来看第第二个坑:
var x = { a: 1, b: { c: 2, d: 3, }, }; x.c = x.b; x.d = x.a; x.b.c = x.c; x.b.d = x.d; var y = JSON.parse(JSON.stringify(x)); console.log(x); /* Uncaught TypeError: Converting circular structure to JSON at JSON.stringify (<anonymous>) at <anonymous>:8:25 */
报错了,其结果表明JSON.parse(JSON.stringify()),
不能拷贝循环引用对象
再来看看Object.assign()
var x = { a: 1, b: { c: 2, d: 3, }, }; x.c = x.b; x.d = x.a; x.b.c = x.c; x.b.d = x.d; var y = Object.assign({}, x); console.log(x); /* [object Object]{ a:1, b:[object, Object], d:[object, Object], d:1 } */
对象字面量的展开操作符目前是ECMAScript
JSON.parse(JSON. stringify ()),
und der Erweiterungsoperator [...
] von ES6
weil in js
The =
-Operator kann keine Kopie für ein Objekt erstellen, es handelt sich lediglich um einen Verweis auf das Objekt var x = [ "a", "b", "c", "d", { e: 1, }, ]; var y = [...x]; console.log(y); //['a', 'b', 'c', 'd', {'e':1}] var m = { a: 1, b: 2, c: ["d", "e"], }; var n = { ...m, }; console.log(n); //{a:1, b:2, c:['d', 'e']}
Auf den ersten Blick wird keine Ausnahme gefunden, denn was wir wollen, ist das gewünschte Ergebnis. Machen Sie die Objektstruktur etwas komplizierter und schauen Sie sich dann das an
function copy(x) { var y = {}; for (m in x) { y[m] = x[m]; } return y; } var o = { a: 1, b: 2, c: { d: 3, e: 4, }, }; var p = copy(o);Ich habe die Falle entdeckt, als ich anfing, also wurde bewiesen, dass
Object.assign()
nur eine flache Kopie des Objekts implementiert
Object.assign()
Beachten Sie außerdem, dass nicht aufzählbare Objekte mit Attributen in der Prototypenkette nicht kopiert werden können: var x = {}; Object.defineProperty(x, "m", { value: 5, writable: false, }); console.log(x.m); //5 x.m = 25; //这一步没报错,但是也没执行 console.log(x.m); //5Es ist überraschend, den Wert von
z
zu erhalten, da x
ist die Prototypenkette von y
, daher wird x
nicht kopiertDas Attribut b
ist ein nicht aufzählbares Attribut Eigenschaft und wird nicht kopiertNur c
Es kann aufgezählt werden, sodass es auch kopiert werden kann. Die oben genannten Fallstricke können auch sehr gut gelöst werden: Tief copy JSON.parse (JSON.stringify())
Object.assign()
kann die Methode kopieren, JSON.parse(JSON.stringify())
nicht 🎜🎜 Schauen wir uns die zweite Falle an : 🎜rrreee🎜 Es wurde ein Fehler gemeldet und das Ergebnis zeigte, dass JSON.parse(JSON.stringify()),
das Zirkelreferenzobjekt nicht kopieren kann🎜🎜Werfen wir einen Blick auf Object. zuweisen()
🎜rrreee🎜Verwenden Sie den Spread-Operator [... ]🎜🎜Der Spread-Operator von Objektliteralen ist derzeit ein Phase-3-Vorschlag von ECMAScript
Objekte einfacher kopieren🎜rrreee🎜Hinweis Der Spread-Operator ist auch eine flache Kopie. Ist es also wirklich so schwierig, Objekte zu kopieren? 🎜🎜Machen Sie Ihre eigenen Räder: 🎜rrreee🎜Manche Leute sagen, dass es keine großen Probleme geben sollte, wenn Sie dies tun. Dann können wir nur lachen und weitermachen 🎜rrreee🎜 Auf diese Weise stößt der Spread-Operator auch hier auf Fallstricke beim Kopieren von Objekten. 🎜🎜Es gibt überall Fallstricke und es ist schwer, sich vor ihnen zu schützen. 🎜🎜Empfohlenes Lernen: 🎜JavaScript-Video-Tutorial🎜🎜Das obige ist der detaillierte Inhalt vonEingehende Analyse von Objektkopiermethoden in JavaScript (mit Code). Für weitere Informationen folgen Sie bitte anderen verwandten Artikeln auf der PHP chinesischen Website!