[Javascript] Object
JS Object, JavaScript object, 객체 리터럴
정의
JavaScript 의 object 는 key-value 쌍의 컬렉션. 거의 모든 non-primitive 값이 객체. 함수, 배열, 정규식도 객체.
const obj = { a: 1, b: 'hi', c: true };
typeof obj // 'object'
생성
// literal (가장 흔함)
const a = { x: 1, y: 2 };
// constructor
const b = new Object();
const c = Object.create(null); // prototype 없는 깨끗한 객체
const d = Object.create({ inherited: 1 }); // 상속
// computed key
const key = 'foo';
const e = { [key]: 1 }; // { foo: 1 }
// shorthand
const x = 1, y = 2;
const f = { x, y }; // { x: 1, y: 2 }
// method shorthand
const g = {
greet() { return 'hi'; } // = greet: function() {...}
};
접근
obj.a // dot notation
obj['a'] // bracket
obj[variable] // 동적 키
// nested
deep.a.b.c
deep?.a?.b?.c // optional chaining
// destructuring
const { a, b } = obj;
const { a: alias } = obj; // rename
const { a = 1 } = obj; // default
const { a, ...rest } = obj; // rest
수정 / 삭제
obj.new = 1;
obj['key'] = 2;
delete obj.a;
// spread
const merged = { ...obj, x: 100 };
const cloned = { ...obj }; // shallow copy
Object 메서드
| 메서드 | 의미 |
|---|---|
Object.keys(obj) | 키 배열 |
Object.values(obj) | 값 배열 |
Object.entries(obj) | [key, value] 쌍 배열 |
Object.fromEntries(entries) | 역변환 |
Object.assign(target, ...src) | 얕은 병합 (target 변경) |
Object.freeze(obj) | 변경 불가 (얕음) |
Object.seal(obj) | 추가/삭제 금지, 수정 OK |
Object.preventExtensions(obj) | 추가만 금지 |
Object.isFrozen / isSealed / isExtensible | 검사 |
Object.getPrototypeOf / setPrototypeOf | 프로토타입 |
Object.getOwnPropertyNames | 모든 own keys (Symbol 제외) |
Object.getOwnPropertySymbols | Symbol 키만 |
Object.getOwnPropertyDescriptor(s) | descriptor |
Object.defineProperty / defineProperties | descriptor 설정 |
Object.create(proto, descriptors) | 생성 |
Object.keys({ a: 1, b: 2 }) // ['a', 'b']
Object.entries({ a: 1, b: 2 }) // [['a', 1], ['b', 2]]
Object.fromEntries([['a', 1]]) // { a: 1 }
property descriptor
각 property 는 4 가지 attribute.
{
value: 1,
writable: true,
enumerable: true,
configurable: true,
}
// 또는 accessor
{
get() { return ... },
set(v) { ... },
enumerable: true,
configurable: true,
}
Object.defineProperty(obj, key, descriptor) 로 명시.
Object.defineProperty(obj, 'x', {
value: 1,
writable: false, // 변경 불가
enumerable: false, // for...in 에서 제외
configurable: false // delete / 재정의 금지
});
키 순서
const obj = { 2: 'a', 1: 'b', name: 'c', [Symbol()]: 'd' };
Object.keys(obj); // ['1', '2', 'name']
// 1. 정수처럼 보이는 키 (오름차순)
// 2. 그 외 string 키 (삽입 순서)
// 3. Symbol 키
동등성
const a = { x: 1 };
const b = { x: 1 };
a === b // false (참조 비교)
// 깊은 비교는 직접
JSON.stringify(a) === JSON.stringify(b) // ⚠️ 순서, 타입 함정
// 또는 lodash _.isEqual
함정
1. 얕은 복사
const a = { x: { y: 1 } };
const b = { ...a };
b.x.y = 99;
a.x.y // 99 (참조 공유)
// 깊은 복사
const c = structuredClone(a); // 모던
const d = JSON.parse(JSON.stringify(a)); // 옛 방식 (date, function 손실)
2. for…in 의 함정
for (const key in obj) {
// prototype chain 의 키도 포함
}
// 안전한 패턴
for (const key in obj) {
if (Object.hasOwn(obj, key)) { ... }
}
// 또는
Object.keys(obj).forEach(key => ...)
3. typeof null
typeof null // 'object' (역사적 버그)
참고
이 글의 용어 (4개)
- [Javascript] Arrayjavascript
- 정의 JavaScript 의 는 순서 있는 객체. 정수 키 + . 풍부한 메서드 (map/filter/reduce/...) 가 함수형 스타일을 지원. 생성 핵심 메서드 (반복) …
- [Javascript] Destructuringjavascript
- 정의 Destructuring 은 배열 또는 객체의 일부를 변수로 풀어내는 ES6 문법. 코드를 짧고 명시적으로. 객체 배열 함수 매개변수 자주 쓰는 idiom API 응답 분해…
- [Javascript] Prototype Chainjavascript
- 정의 JavaScript 의 모든 객체는 (내부 슬롯) 을 가진다. 속성 lookup 시 자신에게 없으면 prototype chain 을 따라 올라가며 검색. 접근 함수의 pro…
- [Javascript] Spread / Restjavascript
- 정의 같은 문법 가 두 가지 의미. - Spread : iterable 을 펼침 (right-hand) - Rest : 나머지를 모음 (left-hand 또는 함수 매개변수) S…
💬 댓글