var a = 5;
var b = 10;
- 변수는 하나의 값을 저장하기 위해 확보한 메모리 공간 또는 메모리 공간을 식별하기 위해 붙인 이름이다.
- 원시 값을 변수에 할당하면 변수(확보된 메모리 공간)에는 실제 값이 저장된다.
- 두 변수는 서로 영향받지 않는다. 즉 각각 다른 메모리 공간에 저장된 별개의 값이다.
값에 의한 전달
- 원시값을 갖는 변수를 다른 변수에 할당하면 원본의 원시값이 복사되어 전달된다.
var a = 5;
var b = a;
b++;
console.log(a)
// 5
console.log(b)
// 6
- 변수 b에 a를 할당했다 하여도, js 엔진은 a의 값을 복사에서 새로운 메모리 공간을 확보해서(변수 b가 가리키는 메모리) 값을 넣어준다.
원시 값과 객체의 비교
참조에 의한 전달
- 참조값은 생성된 객체가 저장된 메모리 주소이다.
let obj1 = {name : 'haha', password: '123'}
let obj2 = obj1;
obj2.password = 'easypeasy';
console.log(obj1)
{name : 'haha', password: 'easypeasy'}
console.log(obj2)
{name : 'haha', password: 'easypeasy'}
- obj2에 obj1을 할당했다 = 메모리 힙의 obj1이 저장된 주소를 할당했다.
- 장점: 결국 두 변수가 가리키는 메모리(객체)는 하나이므로 메모리를 아낄 수 있다.
- 단점: 원시값과 달리, 참조된 객체의 프로퍼티로 저장된 값을 바꾸는 실수를 할 수 있다.
array
var c = [1, 2, 3, 4, 5];
var d = c;
d.push(6)
console.log(d)
[1, 2, 3, 4, 5, 6]
console.log(c)
[1, 2, 3, 4, 5, 6]
다른 배열 만들기
var c = [1, 2, 3, 4, 5];
var d = [].concat(c);
d.push(6)
console.log(d)
[1, 2, 3, 4, 5, 6]
console.log(c)
[1, 2, 3, 4, 5]
object
let obj = {a: 'a', b: 'b', c: 'c'}
let clone = Object.assign({}, obj);
let clone2 = {...obj}
obj.c = 5;
let obj = {a: 'a', b: 'b', c: {deep: 'try and copy me'}}
let clone = Object.assign({}, obj);
let clone2 = {...obj}
obj.c.deep = 'hahaha';
console.log(obj)
//{a: 'a', b: 'b', c: {deep: 'hahaha'}}
console.log(clone)
//{a: 'a', b: 'b', c: {deep: 'hahaha'}}
console.log(clone2)
//{a: 'a', b: 'b', c: {deep: 'hahaha'}}
- 각각의 객체는 참조에 의한 값의 전달이 이뤄진다.
- 상위 객체를 복사하더라도(얕은 복사) 내부 객체까지 복사되지 않는다. 내부 객체는 주소가 복사된다.
객체의 깊은 복사
let superClone = JSON.parse(JSON.stringfy())
- 만약 깊은 복사를 한다면 성능 이슈가 발생할 수 있다. 용량이 큰 객체라면 메모리에 각각 할당되기 때문이다.