IT_Programming/JavaScript

자바스크립트 완벽가이드 - 4.4 기본 타입과 참조 타입

JJun ™ 2010. 7. 4. 18:52


우리가 살펴볼 다음 주제는 변수가 담고 있는 내용에 대한 것이다. 변수는 값을 지니고 있거나 포함한다고

말하곤 한다. 하지만 변수가 포함하고 있는 것이 대체 뭘까? 얼핏 보기에 간단해 보이는 이 질문에 답을

하려면 일단 자바스크립트가 지원하는 데이터 타입들을 살펴봐야 한다. 데이터 타입에는 크게 기본 타입과

참조 타입의 두 가지 종류가 있다.


숫자, 불리언 값, null, undefined 타입은 기본 타입이다.

한편 객체(Object), 배열, 그리고 함수는 참조 타입이다.


기본 타입은 고정된 크기의 메모리를 차지한다. 예를 들어 숫자 타입은 8바이트의 메모리를 차지한다.

불리언 값은 오직 1비트만으로 표현될 수 있다. 숫자 타입은 모든 기본 타입 중에서 가장 크기가 크다.

 

만일 각각의 자바스크립트 변수가 8바이트의 메모리를 할당 받는다면 어떤 기본 타입 값이라도 그 변수에

그대로 저장할 수 있다.[각주:1]


반면 참조 타입은 그렇지 않다. 예를 들어 객체는 어떤 크기라도 가질 수 있다. 즉 객체는 크기가 고정되어 있지 않다. 마찬가지로 배열도 원소 개수에 제한이 없다. 이와 유사하게 함수도 얼마든지 많은 자바스크립트 코드를 포함할 수 있다. 참조 타입은 크기가 고정되어 있지 않기 때문에 참조 타입의 값은 8바이트 메모리를 가지는 변수에 직접 저장할 수 없다. 대신, 변수에 저장되는 것은 이런 값에 대한 '참조'다. 참조는 보통 포인터의 한 종류이거나 메모리 주소이다. 참조는 데이터값 자체가 아니라 그 값을 찾을 수 있는 위치를 변수에게

알려주는 것이다.


기본 타입과 참조 타입을 구별하는 것은 매우 중요하다. 왜냐하면 이 두 가지는 서로 다르게 작동하기

때문이다. 숫자(기본 타입)를 사용하는 다음의 코드를 살펴보자.

 

기본 타입과 참조 타입을 구별하는 것은 매우 중요하다. 왜냐하면 이 두 가지는 서로 다르게 작동하기

때문이다. 숫자(기본 타입)를 사용하는 다음의 코드를 살펴보자.

 

var a = 3.14;      // 변수의 선언과 초기화
var b = a;          // 위 변수의 값을 새로운 변수에 복사한다.
a = 4;               // 원래 변수의 값을 변경한다.
alert(b);           // 3.14가 출력된다. 복사본의 값은 바뀌지 않았다.


위 코드에는 전혀 놀라울 게 없다. 이제, 숫자 대신 배열(참조 타입)을 사용하도록 코드를 살짝 바꾸고

무슨 일이 일어나는지 살펴보자.

 

var a = [1, 2, 3];   // 배열을 참조하도록 변수를 초기화
var b = a;             // 새로운 변수에 참조를 복사
a[0] = 99;            // 원래의 참조를 써서 배열을 변경한다.
alert(b);               // 새로운 참조를 쓰지만 변경된 배열 [99, 2, 3]이 출력된다.


 

위의 결과에 그다지 놀라울 것이 없다면 여러분은 이미 기본 타입과 참조 타입을 구별하는데 익숙한 것이다. 하지만 만일 예상했던 결과가 무언가가 다르다면 위 코드의 두 번째 줄을 주의 깊게 보라. 이 구문에서 변수에 할당되는 것은 배열자체가 아니라 그 배열 값에 대한 참조다. 두 번째 줄이 실행된 후에도 여전히 배열 객체는 하나뿐이다. 그저 이 배열 객체에 대한 두 개의 참조가 있을 뿐이다.


만일 여러분이 기본 타입과 참조 타입을 처음 구별해보는 것이라면 일단 변수의 내용이 무엇인지 항상 유념하라. 기본 타입의 경우 변수에 실제값이 저장되지만 참조 타입의 경우에는 단지 참조만이 저장된다. 기본 타입과 참조 타입의 서로 다른 작동 방식은 앞서 3.15절에서 자세히 파헤쳐본 바 있다.


혹시 눈치 챘을 수도 있겠지만, 필자는 아직 자바스크립트에서 문자열이 기본 타입인지 참조 타입인지 명시하지 않았다. 문자열은 예외적인 경우에 해당한다. 문자열의 크기는 가변적이다. 따라서 고정된 크기의 변수에 문자열을 직접 저장하는 것은 불가능하다. 생각해보자. 효율성을 위해서라면 자바스크립트에서 문자열을 복사할때 그 문자열의 실제 내용물 대신 단지 그에 대한 참조만을 복사할 것 같다. 하지만 많은 경우에 문자열은 마치 기본 타입처럼 작동한다. 사실 문자열이 기본 타입인지 참조 타입인지 논하는 것은 그다지 의미가 없다. 왜냐하면 문자열은 불변(immutable)하기 때문이다. 다시 말하면 문자열 값의 내용을 바꿀 수 있는 방법이 없다. 따라서 앞에서 보았던 배열을 참조로 복사하는 것과 같은 예가 문자열에 대해서는 성립하지 않는다. 결론적으로 여러분이 문자열을 다음 둘 중 어느 것으로 생각해도 별로 상관없다. '문자열은 기본 타입처럼 작동하는 불변의 참조 타입'으로 생각해도 좋고, '문자열은 참조 타입의 효율성을 갖도록 내부적으로 구현된 기본 타입'으로 생각해도 좋다.


        1. 이는 지나치게 단순화시킨 설명이며 실제 자바스크립트 구현을 설명하려는 것은 아니다. [본문으로]