D-story
코어 자바스크립트 - 데이터 타입 본문
데이터 타입에 대해 공부해야 하는 이유
자바스크립트를 이루고 있는 데이터 타입의 종류와 각 데이터 타입의 특징, 처리 과정을 자세하게 파악하여 성능을 고려한 코드 설계와 디버깅에 필요한 지식을 얻기 위해서는 데이터 타입에 대해서 공부할 필요가 있습니다.
데이터 타입의 종류
자바스크립트의 데이터 타입은 크게 기본형 데이터 와 참조형 데이터로 구분됩니다. 기본형 데이터에는 숫자형, 문자열, 불리언, null, undefined, 심볼 등으로 이루어져 있고, 참조형 데이터에는 객체, 배열, 함수 등이 있습니다. 자바스크립트는 객체 기반의 언어로 기본형 데이터를 제외하면 모두 객체로 이루어져 있습니다. 배열과 함수는 객체이며 Date, Map ,WeakMap, Set, WeakSet, ... 등의 자바스크립트의 내장 메소드들은 함수이기 때문에 객체에 해당되고 이들은 모두 참조형 데이터입니다. 자바스크립트는 기본형 데이터와 객체들로 이루어져 있다고도 볼 수 있습니다.
변수 선언과 데이터 할당 원리
변수 a 가 선언되었고, 숫자형 데이터 3 이 할당되었습니다. 변수가 선언되고 그 안에 데이터가 할당되는 원리를 알아보겠습니다.
var a = 3
그 이전에 먼저 식별자와 변수의 차이를 알고 가야 합니다. 식별자는 어떤 데이터를 식별하는데 사용되는 이름인데 쉽게 말해 변수명입니다. 변수의 정의는 변할 수 있는 특정 데이터를 의미하고 식별자가 가리키는 데이터를 의미합니다. 코드 블럭 기준으로 식별자는 a, 변수는 3 이 됩니다.
식별자와 변수의 차이를 알아봤으니 이제 진짜 변수에 데이터 할당되는 원리를 알아보겠습니다.
먼저 아래에 만든 표를 자바스크립트가 사용하는 메모리라고 가정하겠습니다. 메모리의 형태는 추상적으로 표현한 것이고 실제와 완전히 똑같지 않습니다. 추상적으로 표현한 메모리의 형태는 메모리에 데이터를 저장할 각 공간이 있고 각 공간에는 주소 역할을 하는 번호가 매겨져 있습니다. ( 1003번 , 1004번 , 1005번 , ...등, 메모리 주소 번호는 모두 설명을 위한 임의의 주소 번호입니다. )
주소 | ... | 1003 | 1004 | 1005 |
데이터 | 변수 정보 및 데이터 |
변수 a 를 선언하면 자바스크립트는 메모리에 해당 변수 정보를 저장할 공간을 확보합니다. 예시로 1003번 주소의 메모리 공간을 확보했다고 가정하고 1003번의 식별자를 a 로 지정합니다. 그리고 또 다른 메모리 공간에 숫자형 데이터 3을 저장합니다. 그리고 이 숫자형 데이터 3을 저장한 2003번 주소를 1003번의 값으로 대입하게 됩니다.
주소 | ... | 1003 | 1004 | 1005 |
데이터 | 식별자 : a 값 : @2003 |
주소 | ... | 2003 | 2004 | 2005 |
데이터 | 3 |
메모리에 숫자형 데이터 3을 저장하기 전에 하는 일이 있는데, 중복되는 데이터가 있는지 확인하는 일을 합니다. 또 다른 메모리 공간에 숫자형 데이터 3이 있는지 먼저 확인하고 없을 경우에만 새로 메모리 공간을 확보해 숫자형 데이터 3을 저장합니다. 숫자형 데이터 3이 이미 메모리 공간에 있을 경우에는 해당되는 메모리 주소를 값으로 대입하게 됩니다.
var a = 3, b = 3;
예를 들어 변수 a 와 b 가 선언되었고, 둘 다 숫자형 데이터 3 이 할당되었습니다. 코드 순서대로 살펴보면 먼저 변수 a 가 선언되었기 때문에 1003번 주소에 변수 a 를 저장할 공간을 확보합니다. 그리고 숫자형 데이터 3이 할당됩니다. 2003번에 메모리 공간을 확보하고숫자형 데이터 3을 저장합니다.
그 이후에 변수 b 가 선언됩니다. 변수 b 에도 마찬가지로 숫자형 데이터 3 이 할당됩니다. 숫자형 데이터 3 이 메모리 공간에 저장되어 있는지 확인하는데, 변수 a 를 선언하고 3 을 할당하면서 만들어진 숫자형 데이터 3 이 2003번 주소에 이미 존재합니다. 따라서 새로 만들 필요없이 2003번을 변수 b 의 값으로 대입됩니다.
주소 | ... | 1003 | 1004 | 1005 |
데이터 | 식별자 : a 값 : @2003 |
식별자 : b 값 : @2003 |
주소 | ... | 2003 | 2004 | 2005 |
데이터 | 3 |
과정을 순서대로 정리하면 다음과 같습니다. ( 변수 a 에 숫자형 데이터 3이 저장되는 과정을 기준으로 하겠습니다. )
- 변수가 a 가 선언됩니다.
- 메모리에 변수 a 를 저장하기 위한 메모리 주소를 확보합니다.
- 해당 주소의 식별자를 a 로 지정하고, 값은 비워둔 상태가 됩니다.
- 숫자형 데이터 3 을 할당되었고, 메모리에 숫자형 데이터 3이 있는지 확인합니다.
- 숫자형 데이터 3 이 이미 있으면 해당 되는 메모리 주소를 식별자 a 의 값으로 대입하게 됩니다.
- 숫자형 데이터 3 이 메모리에 없으면 새로 메모리 주소를 확보하고 숫자형 데이터 3을 저장한 후, 그 주소를 식별자 a 의 값을 대입하게 됩니다.
참조형 데이터의 할당 원리
이번에는 참조형 데이터의 할당 원리를 알아보겠습니다.
var obj = { a : 1 , b : 2 }
변수 obj 가 선언되고, obj 에 프로퍼티 a와 b를 가진 객체가 할당되었습니다.
선언은 기본형 데이터와 마찬가지로 변수 obj 가 선언되었으니 메모리 주소를 확보하고 obj 를 식별자로 지정합니다. 이 후 값을 대입하는 과정은 기본형 데이터와 다르게 해당 데이터가 있는 메모리 주소를 대입하는 것이 아니고 해당 데이터가 있는 주소들의 묶음을 값으로 대입합니다.
먼저 2003번 주소를 확보합니다. 그리고 객체의 프로퍼티를 저장하기 위한 별도의 주소를 확보합니다. 3003번과 3004번을 만들고 각각 기본형 데이터를 저장하는 과정처럼 4003번과 4004번에 각각 필요한 데이터를 저장하고 식별자에 맞게 모두 대입해줍니다. 그리고 이 프로퍼티들의 주소 범위를 2003번이 저장하는 데이터가 되고 이 주소 범위를 가진 2003번이 최종적으로 1003번, obj 식별자의 값으로 대입되게 됩니다.
주소 | ... | 1003 | 1004 | 1005 |
데이터 | 식별자 : obj 값 : @2003 |
주소 | ... | 2003 | 2004 | 2005 |
데이터 | @3003~@3004 |
주소 | ... | 3003 | 3004 | 3005 |
데이터 | 식별자 : a 값 : @4003 |
식별자 : b 값 : @4004 |
주소 | ... | 4003 | 4004 | 4005 |
데이터 | 1 | 2 |
이번에는 배열을 살펴보겠습니다.
var arr = [1,2]
배열도 객체이기 때문에 객체와 원리는 똑같습니다. 다만 식별자가 원소 번호로 지정됩니다.
메모리 표에 3003번과 3004번의 식별자를 보면 배열의 원소 번호로 지정되어 있는 것을 볼 수 있습니다.
주소 | ... | 1003 | 1004 | 1005 |
데이터 | 식별자 : arr 값 : @2003 |
주소 | ... | 2003 | 2004 | 2005 |
데이터 | @3003~@3004 |
주소 | ... | 3003 | 3004 | 3005 |
데이터 | 식별자 : 0 값 : @4003 |
식별자 : 1 값 : @4004 |
주소 | ... | 4003 | 4004 | 4005 |
데이터 | 1 | 2 |
추가적으로 이번엔 객체에 뎁스가 있는 경우에도 한번 살펴보겠습니다. 조금 과정이 길어질 뿐 크게 다를 건 없습니다.
var obj = {
a : 1
b : {
c : 2
d : 3
}
}
주소 | ... | 1003 | 1004 | 1005 |
데이터 | 식별자 : arr 값 : @2003 |
주소 | ... | 2003 | 2004 | 2005 |
데이터 | @3003~@3004 |
주소 | ... | 3003 | 3004 | 3005 |
데이터 | 식별자 : a 값 : @4003 |
식별자 : b 값 : @4004 |
주소 | ... | 4003 | 4004 | 4005 |
데이터 | 1 | 2 |