js 딥카피와 얕은카피란 무엇이며 어떻게 구현하나요?

php中世界最好的语言
풀어 주다: 2017-11-27 14:51:26
원래의
2230명이 탐색했습니다.

오늘은 JS의 Deep Copy와 Shallow Copy의 차이점과 기능에 대해 알려드리겠습니다. 아래에 예를 들어 보겠습니다.

var m = { a: 10, b: 20 }var n = m;n.a = 15;//이때 m.a의 값은 무엇입니까?

m.a는 얕은 복사본이므로 15를 출력합니다. n과 m이 가리키는 것은 동일한 힙이고, 객체 복사는 복사된 객체의 참조일 뿐입니다.

Deep copy

Deep copy는 객체의 참조를 복사하는 것이 아니라 객체를 완전히 복사하는 위의 얕은 복사와 다릅니다. = { a: 10, b: 20 }var n = {a:m.a,b:m.b};n.a = 15;


이번에도 m.a를 다시 출력했는데 m.a의 값이 여전히 10이고 m 객체와 n 객체는 모두 값이 동일하지만 힙에서는 해당 값이 동일하지 않습니다.

깊은 복사와 얕은 복사

깊은 복사와 얕은 복사의 다이어그램은 대략 다음과 같습니다.


얕은 복사는 개체 자체가 아닌 개체에 대한 포인터만 복사합니다. 같은 기억. 그러나 전체 복사는 동일한 개체를 생성합니다. 새 개체는 원본 개체와 메모리를 공유하지 않으며 새 개체를 수정해도 원본 개체는 변경되지 않습니다.

얕은 복사 구현 방법

1. 간단한 할당을 통해 구현할 수 있습니다

위의 예와 유사하게 다음과 같이 간단한 함수를 캡슐화할 수도 있습니다.

function simpleClone(initalObj) {    
      var obj = {};    
      for ( var i in initalObj) {
        obj[i] = initalObj[i];
      }    
      return obj;
    }
    var obj = {
      a: "hello",
      b:{
          a: "world",
          b: 21
        },
      c:["Bob", "Tom", "Jenny"],
      d:function() {
          alert("hello world");
        }
    }
    var cloneObj = simpleClone(obj); 
    console.log(cloneObj.b); 
    console.log(cloneObj.c);
    console.log(cloneObj.d);
    cloneObj.b.a = "changed";
    cloneObj.c = [1, 2, 3];
    cloneObj.d = function() { alert("changed"); };
    console.log(obj.b);
    console.log(obj.c);
    console.log(obj.d);
로그인 후 복사

2,

Object

. () 구현 Object.sign() 메서드는 소스 객체의 열거 가능한 속성을 원하는 만큼 대상 객체에 복사한 다음 대상 객체를 반환할 수 있습니다. 그러나 Object.sign()은 객체 자체가 아닌 객체의 속성에 대한 참조를 복사하는 단순 복사를 수행합니다.

var obj = { a: {a: "hello", b: 21} };var initalObj = Object.ass({}, obj) initalObj.a.a = "변경됨";console.log(obj.a.a) ; // "changed"


참고: 개체에 레이어가 하나만 있는 경우 전체 복사입니다. 예:

var obj1 = { a: 10, b: 20, c: 30 };var obj2 = Object.assign({}, obj1);obj2.b = 100;console.log(obj1);// { a: 10, b: 20, c: 30 } <-- 沒被改到console.log(obj2);// { a: 10, b: 100, c: 30 }
로그인 후 복사

전체 복사 구현 방법


1. 방법 1은 수동으로 복사하는 것입니다

. 위의 예 마찬가지로 수동 복사를 통해 전체 복사를 수행할 수 있습니다.

2. 개체에 레이어가 하나만 있는 경우 위의 Object.sign() 함수를 사용할 수 있습니다.

3. JSON으로 변환한 다음 다시

var obj1 = { body: { a: 10 } };var obj2 = JSON.parse(JSON.stringify(obj1));obj2.body.a = 20;console.log(obj1);// { body: { a: 10 } } <-- 沒被改到console.log(obj2);// { body: { a: 20 } }console.log(obj1 === obj2);// falseconsole.log(obj1.body === obj2.body);// false
로그인 후 복사

JSON.stringify를 사용하여 개체를

string

으로 변환합니다. 그런 다음 JSON을 사용하여 문자열을 새 객체로 변환합니다. 다음 함수를 캡슐화할 수 있습니다

var cloneObj = function(obj){
    var str, newobj = obj.constructor === Array ? [] : {};
    if(typeof obj !== &#39;object&#39;){
        return;
    } else if(window.JSON){
        str = JSON.stringify(obj), //系列化对象
        newobj = JSON.parse(str); //还原
    } else {
        for(var i in obj){
            newobj[i] = typeof obj[i] === &#39;object&#39; ? 
            cloneObj(obj[i]) : obj[i]; 
        }
    }
    return newobj;};
로그인 후 복사

4. 재귀 복사

function deepClone(initalObj, finalObj) {    
  var obj = finalObj || {};    
  for (var i in initalObj) {        
    var prop = initalObj[i];        // 避免相互引用对象导致死循环,如initalObj.a = initalObj的情况
    if(prop === obj) {            
      continue;
    }        
    if (typeof prop === &#39;object&#39;) {
      obj[i] = (prop.constructor === Array) ? [] : {};            
      arguments.callee(prop, obj[i]);
    } else {
      obj[i] = prop;
    }
  }    
  return obj;}var str = {};var obj = { a: {a: "hello", b: 21} };deepClone(obj, str);console.log(str.a);
로그인 후 복사

5. Object.create() 메서드를 사용하세요

전체 복사 효과를 얻으려면 var newObj = Object.create(oldObj)를 직접 사용하세요.

function deepClone(initalObj, finalObj) {    
  var obj = finalObj || {};    
  for (var i in initalObj) {        
    var prop = initalObj[i];        // 避免相互引用对象导致死循环,如initalObj.a = initalObj的情况
    if(prop === obj) {            
      continue;
    }        
    if (typeof prop === &#39;object&#39;) {
      obj[i] = (prop.constructor === Array) ? [] : Object.create(prop);
    } else {
      obj[i] = prop;
    }
  }    
  return obj;}
로그인 후 복사

6. jquery

jquery는 Deep Copy에 사용할 수 있는 $.extend를 제공합니다.

var $ = require(&#39;jquery&#39;);var obj1 = {
    a: 1,
    b: { f: { g: 1 } },
    c: [1, 2, 3]};var obj2 = $.extend(true, {}, obj1);console.log(obj1.b.f === obj2.b.f);// false
로그인 후 복사

7. lodash

또 다른 매우 인기 있는 함수 라이브러리인 lodash도 Deep Copy를 위한 _.cloneDeep을 제공합니다.

var _ = require(&#39;lodash&#39;);var obj1 = {
    a: 1,
    b: { f: { g: 1 } },
    c: [1, 2, 3]};var obj2 = _.cloneDeep(obj1);console.log(obj1.b.f === obj2.b.f);// false
로그인 후 복사

이것은 성능이 좋고 사용하기 매우 쉽습니다.

이 사례를 읽으신 후 방법을 마스터하셨다고 생각합니다. 더 흥미로운 정보를 보려면 PHP 중국어 웹사이트의 다른 관련 기사를 주목하세요!


관련 읽기:

HTML에서 텍스트 마지막 줄의 불완전한 표시를 처리하는 방법


css3을 사용하여 아이콘 효과를 만드는 방법


CSS 인코딩을 변환하는 방법

위 내용은 js 딥카피와 얕은카피란 무엇이며 어떻게 구현하나요?의 상세 내용입니다. 자세한 내용은 PHP 중국어 웹사이트의 기타 관련 기사를 참조하세요!

관련 라벨:
원천:php.cn
본 웹사이트의 성명
본 글의 내용은 네티즌들의 자발적인 기여로 작성되었으며, 저작권은 원저작자에게 있습니다. 본 사이트는 이에 상응하는 법적 책임을 지지 않습니다. 표절이나 침해가 의심되는 콘텐츠를 발견한 경우 admin@php.cn으로 문의하세요.
인기 튜토리얼
더>
최신 다운로드
더>
웹 효과
웹사이트 소스 코드
웹사이트 자료
프론트엔드 템플릿