- 저자
- 정재남
- 출판
- 위키북스
- 출판일
- 2019.09.10
<목표> JS 핵심 개념 정확히 이해하기
- 데이터 타입, 실행 컨텍스트와 스코프, 호이스팅, 콜백함수, this, 클로저, 프로토 타입
- 원리를 이해하자
- 왜? -> 왜? -> ... 깊게 파고드는 집요함을 갖자
- 데이터 타입
기본형 & 참조형
어떻게 구분되는걸까? : 불변성
bit : 0 또는 1 값을 갖는 메모리 조각
각 비트는 고유한 식별자(메모리 주소값)로 위치를 확인(검색)한다
비트 단위로 위치를 확인하는건 비효율적인 -> 몇개씩 묶자 = byte (8bit)
C/C++, Java : 정적 타입 언어
메모리 낭비 최소화를 위해 데이터 타입 별로 메모리 영역 크기 정해둠
JS: 메모리 용량이 커진 상태에서 등장한 언어, 상대적으로 메모리 관리 필요성 ⬇️
- 변수 vs. 식별자
변수 = 변할 수 있는 무언가 (변할 수 있는 데이터)
식별자 = 어떤 데이터를 식별하는 이름 = 변수명 - 변수 선언의 동작 원리
var a; // 변할 수 있는 데이터를 만들고, 이름(식별자)을 a라 한다. undefined반환
a = '5' // 변경 가능한 데이터가 담기는 공간 = 변수
메모리 관점
변수 영역, 데이터 영역이라는 용어는 이해를 돕기 위한 용어임.
1001 이라는 빈 공간을 확보하고, 공간의 이름을 a 라 한다. = 식별자
다른 빈공간 5003에 '5'를 저장하고, 그 주소 (5003)을 a에 저장한다.
변수 a에 접근할때는 a 식별자를 검색
왜 변수와 데이터를 별도의 메모리 공간에 저장할까?
JS는
숫자형에 64bit 할당,
문자열에는 미리 할당X (한글, 영어, 글자수에 따라 가변적임)
=> 미리 확보한 공간 내에서만 데이터 변환이 가능하다면 추가로 데이터 크기에 맞게 늘리는 작업이 필요하다
= 예) 1002, 1003에 데이터가 있는 상태에서 1002 에 있는 데이터를 늘리려고하면? 1003에 있는 데이터를 1002 추가할 길이만큼 뒤로 이동한다음에 1002를 늘린다
= 컴퓨터 연산이 많아짐
-> 변수와 데이터를 별도의 공간에 저장하는게 효율적이다
- 예) 500개 변수마다 숫자 5를 할당한다면
숫자형 = 8 byte x 500개 = 4000 byte 가 필요함 - 변수와 데이터를 별도의 공간에 저장하면 (주소 공간의 크기가 2byte라고할때)
= (500개 x 2 byte) + 8 byte (숫자형) : 500개 변수마다 주소값만 달아주면 되고, 실제 데이터는 1개만 있으면 됨 - a = 'abc'로 재할당한다면
5003에 '5'를 수정하는 것이 아니라 새로운 'abc'를 5002에 저장 후 식별자 a 가 바라보는 메모리 주소값을 변경시킨다.
5003 주소를 참고하는 변수(= 참조 카운트)가 0개이면 가비지 컬렉터 GC의 수거 대상이 된다.
변수 vs 상수
변수와 상수를 구분하는 것 = 변경 가능성
(변수는 변하는 데이터, 상수는 변하지않는 데이터)
상수 vs 불변값
기본형 데이터 = 불변성을 갖는다
이때 불변성은 '데이터 영역'의 메모리의 특성이다.
ex. 숫자형, 문자열, boolean, null, undefined, Symbol
var a = 'abc'; // 빈 공간 1001 을 a 라는 식별자로 저장하고 & 빈 공간 5002에 값 'abc'를 저장한다. a 가 @5002 주소값을 바라보게한다.
a = a + 'def'; // 빈공간 5004에 새로운 값 'abcdef'를 저장하고, a 의 값을 @5004로 변경한다.
var b = 5; // 빈공간 1003의 이름을 b라고 한다. & 빈공간 5003에 5를 저장한다 & b에 5003 주소값을 저장한다.
var c = 5; // 빈공간 1004의 이름을 c라고 한다. 데이터 영역에서 5를 찾는다. 이미 만들어놓은 주소를 재활용한다. @5003을 저장한다.
b = 7; // 데이터 영역에서 7을 찾는다. 없다 -> 새로 만든다 5001에 저장한다. -> b가 바라보고 있는 주소값을 5001로 수정한다
각각의 데이터는 다른 값으로 변경할 수 없다 = 불변성 (GC에 의해 수거되지 않는 한)
여기서 궁금했던 점
호이스팅은 어떻게 일어나는걸까?
변수 영역에서 해당 변수명이 있는지 먼저 검사하기 때문인가? 그때는 값이 할당된 주소값을 알 수 없나?
const 로 선언한 상수는 변수명 & 주소값<- 여기에 다른 주소값이 못들어오는건가?
const myArr = [] 하고 push 로 값이 추가되는건 ?
const 로 선언해서 주소값 변경이 안된다면 어떻게 데이터가 추가되는걸까?
참조형 데이터 = 가변성을 갖는다?
var obj1 = {a:1, b: 'bbb'}
빈 공간 1001 을 확보하고 이름을 obj1라고 한다.
데어터가 여러 프로퍼티로 이루어진 데이터 그룹임 -> 별도의 변수 영역 (@7001 ~ ) 을 마련하고 그 주소를 @5004에 저장한다.
7001과 7002에 각각 이름 a, b라는 프로퍼티 이름을 지정한다.
데이터 영역에서 1을 검색한다. 없음 -> 빈공간에 저장
7001에 @5002 주소를 저장한다.
>객체 프로퍼티(변수) 영역만 별도로 갖고, 기존 데이터 영역은 그대로 사용한다.
>즉 데이터 영역에 저장된 값은 모두 불변값이다.
obj.a = 2;
7001에 있는 a가 바라보는 주소값은 5001로 바뀜.
그러나 @ 1001 에 있는 obj1 가 바라보는 주소값 @5004 는 바뀌지 않는다. 기존 객체 내부만 바뀜
참조형 데이터는 불변하지 않다.
위에서 했던 질문의 답을 알 수 있다.
> - const 로 선언한 상수는 변수명 & 주소값<- 여기에 다른 주소값이 못들어오는건가?
> => 그렇다. 처음에 저장한 주소값은 안바뀜
> - const myArr = `[ ]`하고 push 로 값이 추가되는건 ?
> const 로 선언해서 주소값 변경이 안된다면 어떻게 데이터가 추가되는걸까?
> => 별도의 변수 영역이 존재한다.
- 깊은 복사 (기본형), 얕은 복사(참조형)
- 복사 과정은 동일하다. 원본 데이터가 변경될 때 결과가 다름
var a = 10; var b = a; // 같은 주소값을 바라봄 = 데이터 = 불변 var obj1 = {c: 10, d:'ddd'} var obj2 = obj1 // 같은 주소값을 바라봄 = 다른 데이터를 참조하고 있음
b = 15;
obj2.c = 20;
객체가 바라보는 주소값 @5003 은 바뀌지 않았지만 ( = 불변)
@5003이 바라보는 주소값 @7001~ 안의 변수가 바라보는 주소값이 바뀌었음
따라서 원본 객체도 데이터가 변하게됨
- 불변 객체
객체의 내부 프로퍼티를 바꿔야 할때 새로운 객체를 만들어 할당 => 불변성 확보
언제 요구되는가?
ex. 이름을 바꾸는 함수
1) 객체 프로퍼티에 접근해 값을 수정한다 -> 원본 값이 같이 변경됨
2) 새로운 객체를 반환하도록 한다 -> 원본 객체 변하지 않음
3) 중첩된 참조형의 데이터라면? 프로퍼티에 대해서도 새로운 객체를 반환하도록 해야함
4) JSON -> 문자열 -> JSON 으로 객체를 복사한다
- undefined
(1) 사용자가 명시적으로 지정
또는
(2) 자바스크립트 엔진이 자동으로 부여
- 값을 대입하지 않은 변수
: 데이터 영역의 메모리 주소를 지정하지 않은 식별자에 접근할때
- 객체 내부에 존재하지 않는 프로퍼티에 접근
- return문이 없거나 호출되지 않은 함수의 실행 결과
- 빈 값 ≠ undefined
길이가 3인 배열 Array(3) : `[empty*3]
길이만큼 index 가 있을 것 같지만 특정 index에 값을 지정할때만! 비로소 빈 공간을 확보하고, 인덱스를 이름으로 하고, 데이터가 있는 주소값을 저장한다. (배열은 객체다)
undefined
(1) 사용자에 의해 명시될때 = 값 자체
(2) JS 엔진에 의해 부여될때 = 값이 없음
var a;
undefined가 자동으로 할당되는 것이 아님. a에 접근할때 = 값이 할당되지 않은 변수에 접근할 때 반환값으로 undefined를 줄 뿐.
항상 JS 엔진에 부여되는 경우에 해당하도록, 값이 없음을 나타낼 때는 null 을 사용하자
- null
`type of null // object`
js 자체 버그임
var n = null
n == undefined // true
n = null // true
n === undefined // false
n === null // true
이 포스팅은 <코어 자바스크립트> 를 읽고 내용을 정리한 포스팅입니다.
틀린 내용이 있다면 알려주세요 _ _
'개발 공부 일지 > 코어 자바스크립트 (정재남)' 카테고리의 다른 글
[코어 자바스크립트] 클로저 개념 (0) | 2025.03.04 |
---|---|
[코어 자바스크립트] 비동기 제어로 콜백 지옥 탈출하기 (1) | 2025.02.25 |
[코어 자바스크립트] 콜백 함수 (0) | 2025.02.25 |
[코어 자바스크립트] this - 명시적 바인딩 (0) | 2025.02.21 |
[코어 자바스크립트] this - 규칙 (0) | 2025.02.21 |