瞭解什麼是淺拷貝與深拷貝之前,首先要明白JavaScript中值類型與引用類型的存儲特征。1. 值類型分為兩種:基本數據類型:string、number、boolearn、undefined、null複合數據類型:Array、Object、Function、Date、RegExp…… 2. 賦值`` ...
瞭解什麼是淺拷貝與深拷貝之前,首先要明白JavaScript中值類型與引用類型的存儲特征。
1. 值類型分為兩種:
基本數據類型:string、number、boolearn、undefined、null
複合數據類型:Array、Object、Function、Date、RegExp……
2. 賦值
```2.1基本數據類型賦值示例
var num = 123;
var num2 = num;
```
* 值類型賦值的存儲特點, 將變數內的數據全部拷貝一份, 存儲給新的變數.
* `var num = 123` 表示變數中存儲的數字是 123.
* 然後將數據拷貝一份,就是將 123 拷貝一份. 那麼記憶體中有 2 個 數據
* 將拷貝數據賦值給 `num2`,num2的變數值改變不會影響num的變數值
* 其特點是在記憶體中有**兩個數據副本**.
```2.2複合數據類型賦值示例
var o = { name: '張三' };
var obj = o;
```
* 賦值就是將 變數 o 中存儲的數據拷貝一份, 然後將該數據賦值給 obj
* 特點是記憶體中只有 1 份數據,對象o和對象obj的name屬性值都指向同一個地址。
* 問題: 修改 對象obj中 的 name 屬性會影響到 原來對象o 中的 name屬性對應的值。
那麼問題來了,複合數據類型怎麼才可以將值賦值給另外一個對象,並且在另外一個對象修改值的情況下不影響自身的值呢?
下麵就說一下我理解的深拷貝與淺拷貝:
# 深拷貝與淺拷貝
1. 什麼是深拷貝, 什麼是淺拷貝
淺拷貝:*只針對當前對象的屬性進行拷貝,而噹噹前對象的屬性是引用類型時,這個不考慮。
*屬性是引用類型,拷貝後引用的是地址,如果進行更改,會影響拷貝的對象屬性。
深拷貝:*針對當前對象的數據的所有引用結構都拷貝一份,數據在記憶體中是獨立的。
*屬性是引用類型,如果進行更改,不會影響拷貝的對象屬性。
2. 實現深拷貝的代碼封裝
var deepCopy = function () {
// 1, 創建一個對象
var temp = {};
// 2, 拷貝屬性, 判斷如果是引用類型需要深拷貝
for ( var k in this ) {
if ( typeof this[ k ] === 'object' ) {
temp[ k ] = this[ k ].deepCopy();
} else {
temp[ k ] = this[ k ];
}
// temp[ k ] = this[ k ];
}
// 3, 返回對象
return temp;
};
測試示例:
var car = { name: '法拉利' };
var p = { name: '張三', age: 19, gender: '男', car: car };
//給對象car和對象p動態添加 拷貝的 方法
car.deepCopy = deepCopy;
p.deepCopy = deepCopy;
//重新定義一個newP對象,將對象p中的所有屬性與方法都賦值給newP。
var newP = p.deepCopy();
//這個時候修改對象p中的屬性方法對應的值時,如果在沒有調用封裝的深拷貝的函數時,newP的值也會相應改變。
//調用了深拷貝的函數之後,即使對象p中的值改變,也不會影響newP中值。
p.name = '李四';
p.age = 20;
p.gender = '女';
p.car.name = '蘭博基尼';
以上就是實現深拷貝的方法。