2016-11-10 4 views
3

У меня есть следующий код:Почему мой исходный массив получает сращивание, если я соединяю клонированный массив в JavaScript?

var coords = [ 
    {lat: 39.57904, lng: -8.98094, type: "a"}, // A 
    {lat: 39.55436, lng: -8.95493, type: "b"}, // B 
    {lat: 39.56634, lng: -8.95836, type: "c"} // C 
]; 

var travelingOptions = []; 

getAllTravelingOptions(); 

function getAllTravelingOptions(){ 
    coords.forEach((point, pos) => { 
     let c = coords; 
     delete c[pos]; 
     console.log(c); 
     console.log(coords); 
    }); 
} 

Почему это переменная c и coords всегда одинаковы? Если я удалю по c, он отображает действие на coords. Это нормальное поведение?

+2

'' c' и coords' являются ссылки на тот же объект. – Amy

ответ

1

Из-за назначения c вы получаете ссылку на массив coords.

Любое изменение coords делает эффект c, пока не будет присвоено новое значение c.

Если вы сделаете копию массива с Array.slice, вы получите новый массив, но с той же ссылкой объектов. При изменении одного объекта внутри вы меняете один и тот же объект с той же ссылкой в ​​c.

var coords = [ 
 
     {lat: 39.57904, lng: -8.98094, type: "a"}, // A 
 
     {lat: 39.55436, lng: -8.95493, type: "b"}, // B 
 
     {lat: 39.56634, lng: -8.95836, type: "c"} // C 
 
    ], 
 
    c = coords.slice(); 
 

 
console.log(c); 
 
coords[1].type = 'foo'; 
 
console.log(c);
.as-console-wrapper { max-height: 100% !important; top: 0; }

1

Назначение не клонировать массив он только создает ссылку на объект/первоначально массива. Вы можете использовать Array.prototype.slice() сделать неполную копию:

let c = coords.slice(); 
1

Это происходит потому, что c и coords Теперь ссылаются на тот же объект. Чтобы предотвратить это, используйте let c = coords.slice(), чтобы создать копию coords и назначить ее c.

let original = [1, 2, 3, 4]; 
 
let test = original; 
 
let testSlice = original.slice(); 
 

 
original[0] = 12345; 
 

 
console.log('test: ', test) 
 
console.log('testSlice: ', testSlice)

Однако, новый массив все равно будет ссылаться на одни и те же объекты, что старый массив сделал. Быстрое исправление для этого было бы «клонированием» этих объектов.

let objs = [ 
 
    {'obj': 1}, 
 
    {'obj': 2}, 
 
    {'obj': 3} 
 
]; 
 

 
let newArr = []; 
 

 
objs.forEach(obj => { 
 
\t let newObj = {}; 
 
\t Object.keys(obj).forEach(key => { 
 
    \t newObj[key] = obj[key]; 
 
    }); 
 
    newArr.push(newObj); 
 
}); 
 

 
console.log('old: ', objs) 
 
console.log('new: ', newArr) 
 

 
newArr[0].obj = 12345; 
 

 
console.log('old after changing obj on new: ', objs)