객체 리터럴
자바스크립트는 객체 기반의 프로그래밍 언어이며, 원시 값을 제외한 나머지 값 (함수, 배열, 정규 표현식 등)은 모두 객체이다. 또한 원시 값은 변경 불가능(immutable)한 값이지만 객체는 변경 가능(mutable)한 값이다
- 프로퍼티: 객체의 상태를 나타내는 값(data)
- 메서드: 프로퍼티(상태 데이터)를 참조하고 조작할 수 있는 동작(behavior)
var person = {
name: 'Lee'
};
// 마침표 표기법에 의한 프로퍼티 접근
console.log(person.name); // Lee
// 대괄호 표기법에 의한 프로퍼티 접근
console.log(person['name']); // Lee
프로퍼티는 두 가지 방법으로 접근할 수 있다
* 대괄호 표기법의 경우 키는 반드시 문자열이어야 한다
var person = {
name: 'Lee'
};
console.log(person.age); // undefined
객체에 존재하는 않는 프로퍼티에 접근하면 레퍼런스 에러가 아닌 undefined를 반환한다
// ES6
let x = 1, y = 2;
// 프로퍼티 축약 표현
const obj = { x, y };
console.log(obj); // {x: 1, y: 2}
const obj = {
name: 'Lee',
// 메서드 축약 표현
sayHi() {
console.log('Hi! ' + this.name);
}
};
obj.sayHi(); // Hi! Lee
ES6 이후 객체 내부에 프로퍼티, 메서드를 축약할 수 있다
* 다만 메서드는 축약할 경우 프로토타입이 없어 생성자 함수로 사용할 수 없다!
원시 값과 객체의 비교
자바스크립트의 원시 값(primitive)은 객체가 아니면서 메서드도 가지지 않는 데이터이다
* string, number, bigint, boolean, undefined, symbol, null 7종류가 존재
var str = 'string';
// 문자열은 유사 배열이므로 배열과 유사하게 인덱스를 사용해 각 문자에 접근할 수 있다.
// 하지만 문자열은 원시값이므로 변경할 수 없다. 이때 에러가 발생하지 않는다.
str[0] = 'S';
console.log(str); // string
자바스크립트 문자열은 기본적으로 변경할 수 없다 (재할당은 메모리 주소의 변경)
var str = 'string';
// 문자열은 유사 배열이므로 배열과 유사하게 인덱스를 사용해 각 문자에 접근할 수 있다.
console.log(str[0]); // s
// 원시 값인 문자열이 객체처럼 동작한다.
console.log(str.length); // 6
console.log(str.toUpperCase()); // STRING
다만 문자열은 length 값을 가지며 인덱스로 문자에 접근할 수 있는 유사 배열 객체이다
var score = 80;
// copy 변수에는 score 변수의 값 80이 복사되어 할당된다.
var copy = score;
console.log(score, copy); // 80 80
console.log(score === copy); // true
// score 변수와 copy 변수의 값은 다른 메모리 공간에 저장된 별개의 값이다.
// 따라서 score 변수의 값을 변경해도 copy 변수의 값에는 어떠한 영향도 주지 않는다.
score = 100;
console.log(score, copy); // 100 80
console.log(score === copy); // false
값에 의해 전달된 값은 다른 메모리 공간에 저장된 별개의 값이다
// const 키워드를 사용해 선언한 변수는 재할당이 금지된다. 상수는 재할당이 금지된 변수일 뿐이다.
const o = {};
// const 키워드를 사용해 선언한 변수에 할당한 원시값(상수)은 변경할 수 없다.
// 하지만 const 키워드를 사용해 선언한 변수에 할당한 객체는 변경할 수 있다.
o.a = 1;
console.log(o); // {a: 1}
원시 값은 변경할 수 없는 상수지만 객체의 프로퍼티는 재할당이 가능하다
객체는 프로퍼티 할당을 위해 한 단계를 더 거치기 때문에 내부적으로 변경 가능한 값이다
* 불변 객체: Object.freeze()가 아닌 객체를 깊은 복사하고 프로퍼티를 변경한 후 바꿔 치는 기법을 의미
var person = {
name: 'Lee'
};
// 참조값을 복사(얕은 복사). copy와 person은 동일한 참조값을 갖는다.
var copy = person;
// copy와 person은 동일한 객체를 참조한다.
console.log(copy === person); // true
// copy를 통해 객체를 변경한다.
copy.name = 'Kim';
// person을 통해 객체를 변경한다.
person.address = 'Seoul';
// copy와 person은 동일한 객체를 가리킨다.
// 따라서 어느 한쪽에서 객체를 변경하면 서로 영향을 주고 받는다.
console.log(person); // {name: "Kim", address: "Seoul"}
console.log(copy); // {name: "Kim", address: "Seoul"}
얕은 복사(1단계만 복사) ~ 깊은 복사(재귀적으로 원시 값까지 전부 복사)
var person1 = {
name: 'Lee'
};
var person2 = {
name: 'Lee'
};
console.log(person1 === person2); // false
console.log(person1.name === person2.name); // true
즉, 자바스크립트에는 참조에 의한 전달은 존재하지 않고 값에 의한 전달만이 존재한다
Reference🔽
본 내용은 위키북스의 '모던 자바스크립트 Deep Dive'를 바탕으로 작성되었습니다.
'Languages > JavaScript' 카테고리의 다른 글
[HUFS/GnuVil] #6 실행 컨텍스트, 스코프 (0) | 2022.10.02 |
---|---|
[HUFS/GnuVil] #5 함수 (0) | 2022.09.20 |
[HUFS/GnuVil] #3 제어문, 타입변환과 단축평가 (1) | 2022.09.20 |
[HUFS/GnuVil] #2 데이터 타입, 연산자 (0) | 2022.09.14 |
[HUFS/GnuVil] #1 변수, 표현식과 문 (0) | 2022.09.14 |