관리 메뉴

흰둥씨의 개발장

[자바스크립트] 딥다이브) 원시값과 객체의 비교 본문

BoOk/JS deep dive

[자바스크립트] 딥다이브) 원시값과 객체의 비교

돈워리비해삐 2023. 5. 17. 22:33

- 원시 타입 (primitive type)

ㄴ원시 값은 변경불가능한 값(immutable value)

ㄴ원시 값을 변수에 할당하면 변수(확보된 메모리)에 실제 값이 저장됨 

ㄴ원시 값을 갖는 변수를 다른 변수에 할당하면 원본값이 복사되어 전달됨(값에 의한 전달)

 

- 객체 타입 (object/ reference type) 

ㄴ객체는 변경가능한 값(mutable value)

ㄴ객체를 변수에 할당하면 변수에 참조 값 저장됨 

ㄴ객체를 가리키는 변수를 다른 변수에 할당하면 원본의 참조 값이 복사되어 전달(참조에 의한 전달)

 

1) 원시값 

  - 1) 변경 불가능한 값 (불변성)

ㄴ한번 생성된 원시값은 읽기 전용 값= 불변 = 데이터 신뢰성 보장 

ㄴ재할당하면 변수가 참조하던 메모리 공간의 주소 변경됨 (할당된 원시값이 변경 불가능한 값이기 때문)

ㄴ불변성을 갖는 원시값을 할당한 변수는 재할당 이외에 변수값을 변경할 수 있는 방법이 없음 

  - 2) 문자열과 불변성

ㄴECMAscript사양에 문자열, 숫자이외의 원시타입은 크기를 명확히 규정하고 있지 않아 브라우저 제조사 따라 크기다름 

ㄴ문자열은 1개의 문자당 2바이트의 공간 필요 / 숫자는 1이나 10000이나 똑같이 8바이트공간소요

ㄴ자바스크립트는 문자열 타입제공, 원시타입으로 변경불가능함 (but C언어에서는 문자열타입 존재 하지않음)

ㄴ문자열은 유사배열 객체 이면서, 이터러블임 (배열과 유사하게 접근가능)

// 유사객체 ?  마치 배열처럼 인덱스로 프로퍼티 값에 접근, length프로퍼티를 갖는 객체

let str = 'string';
str[0] = 'H'; // 변경 해도 반영은 안됨 => 문자열은 변경 불가능한 값이기 때문
console.log(str) // string

  - 3) 값에 의한 전달 (=메모리 주소전달 , 메모리 주소를 통해 메모리 공간에 접근하면 값을 참조함)

ㄴ변수에는 값이 전달되는 것이 아니라 메모리 주소가 전달됨 (식별자가 기억하고 있는 메모리주소를 통해 메모리 공간에 저장된 값에 접근)

let merong = 425;
let copy = merong;

console.log(merong === copy);  //true
copy = 100;

console.log(merong, copy); // 425 100
console.log(merong === copy);  //false

//두변수의 원시값은 서로 다른 메모리공간에 저장된 별개의 값이 되어 어느 한쪽에서 재할당을 통해 값을 변경하더라도 서로 간섭할수없음

 

 

2) 객체 

ㄴ프로퍼티 개수가 정해져있지 않고, 동적으로 추가 삭제 가능 , 프로퍼티 값에 제약없음 (메모리 공간 크기 사전에 정해둘수 없음)

ㄴ자바스크립트는 클래스 없이 객체 생성 가능 (C++, 자바 같은 언어는 사전정의된 클래스로 객체생성하고, 이후 프로퍼티 삭제 추가 불가)

ㄴV8자바스크립트 엔진에서는 동적탐색대신 히든 클래스 방식으로 프로퍼티 접근해서 비효율 고침

  - 1) 변경 가능한 값 

ㄴ객체(참조)타입의 값(=객체)은 변경가능한 값

ㄴ객체를 할당한 변수는 재할당 없이 객체를 직접 변경 할수 있음 (=참조 값은 생성된 객체가 저장된 메모리 주소 그 자체임)

ㄴ여러개의 식별자가 하나의 객체를 공유할 수 있음 

let 명탐정 = {}; 
명탐정.name = 'conan';
명탐정.address = '베이커가 221b';

console.log(명탐정); //{ name: 'conan' , address: '베이커가 221b' }

let 찐탐정 = { ...명탐정, new : {name : '셜록'} }; // 얕은복사
console.log(찐탐정); //{ name: 'conan' , address: '베이커가 221b' , new : {name : '셜록'}}

**얕은 복사 : 객체를 한단계까지만 복사

**깊은 복사 : 객체에 중첩되어있는 객체까지 모두 복사

 

  - 2) 참조에 의한 전달 

ㄴ객체를 가리키는 변수를 다른 변수에 할당하면 원본의 참조값이 복사 되어 전달 되는 것 

ㄴ두개의 식별자가 하나의 객체를 공유하는 것 

ㄴ원본 또는 사본중 어느 한쪽에서 객체를 변경하면 서로 영향을 받는다. 

let people1 = {
	name : 'Cho',
    };

let copy = people1;
    
let people2 = {
	name : 'Cho',
    };
    
 console.log(people1 === people2);  //false (메모리 주소 다름)
 console.log(people1 === copy);  	//true
 console.log(people1.name === people2.name);  //true