모던 자바스크립트 Deep Dive 정리
1. 자바스크립트 객체의 분류
1-1. 표준 빌트인 객체
1-2. 호스트 객체
1-3. 사용자 정의 객체
2. 표준 빌트인 객체
▶ ECMAScript 사양에 정의된 객체로, 브라우저 혹은 Node.js 에서도 사용 가능
▶ 전역 객체의 프로퍼티로 제공되므로, 별도의 선언 없이 전역 변수처럼 사용 가능
▷ Object, String, Math, Map/Set, Promise 등
▶ Math, Reflect, JSON 을 제외한 빌트인 객체들은 생성자 함수 객체이기 때문에 인스턴스 생성 가능
▷ 인스턴스의 프로토타입은 빌트인 객체.prototype 에 바인딩 된다
▶ 표준 빌트인 객체들은 인스턴스 없이 호출 가능한 빌트인 정적 메서드를 제공한다
▷ 예) Number.isInteger(숫자) -> 정수인지 판별
3. 원시값과 래퍼 객체
▶ 원시값인 문자열이 마치 객체처럼 동작할 때가 있다
const str = 'hello';
// 원시 타입인 문자열이 프로퍼티와 메서드를 갖고 있는 객체(인스턴스)처럼 동작한다.
console.log(str.length); // 5
console.log(str.toUpperCase()); // HELLO
// 래퍼 객체인 String 생성자 함수의 인스턴스가 생성되고,
// 문자열은 래퍼 객체의 [[StringData]] 내부 슬롯에 할당된다
// 문자열 래퍼 객체인 String 생성자 함수의 인스턴스는 String.prototype의 메서드를 상속받아 사용
▶ 이는 자바스크립트 엔진이 일시적으로 원시값을 연관된 객체(래퍼 객체)로 변환해주기 때문이다
▶ 래퍼 객체
▷ 문자열, 숫자, 불리언 값에 대해 객체처럼 접근하면 생성되는 임시 객체
4. 전역 객체
▶ 가장 먼저 생성되고, 어떤 객체에도 속하지 않은 최상위 객체
▷ 브라우저 환경 : window
▷ Node.js 환경 : global
▷ ES11 에서는 globalThis 추가 (브라우저 + Node.js 환경 공통)
▶ 모든 표준 빌트인 객체, 호스트 객체 및 var로 선언한 전역 변수와 전역 함수를 프로퍼티로 갖는다
▷ 암묵적 전역 변수도 프로퍼티로 갖는다
▶ 브라우저 환경의 모든 자바스크립트 코드는 하나의 전역 객체 window를 공유한다
4-1. 빌트인 전역 프로퍼티
▶ 전역 객체의 프로퍼티로, 전역에서 사용되는 값을 제공
▷ 전역 객체의 프로퍼티이므로, window.Infinity 처럼 사용 가능
▶ Infinity / -Infinity
▷ typeof 연산자로 확인하면 number로 판별
▶ NaN
▷ Not-a-Number 를 의미
▷ typeof 연산자로 확인하면 number로 판별
▶ undefined
▷ 원시타입 undefined를 값으로 가짐
4-2. 빌트인 전역 함수
eval(param)
▷ param : 자바스크립트 코드 문자열
▷ return : 전달받은 문자열 코드가 표현식이면 그 값을 리턴, 표현식이 아닌 문이면 undefined 리턴
▷ 여러개의 문을 전달받으면 마지막 결과를 리턴
▷ 기존의 스코프를 런타임에 동적으로 수정 (즉, 전달된 코드를 그 자리에 있던 코드처럼 실행)
▷ 사용 금지 (처리속도 매우 느리고, 입력받은 코드 수행시 보안 우려)
isFinite(number)
▶ 유한수이면 true, 무한수이면 false, 숫자로 변환할 수 없는 값이면 undefined 반환
isNaN(number)
▶ 전달받은 인수가 NaN이면 true, 숫자이면 false, NaN으로 변환될 수 있는 값이면 true
parseFloat(string)
▶ 전달 받은 문자열을 실수로 해석하여 반환
▷ 숫자로 변환할 수 없으면 NaN 반환
▷ 앞뒤 공백을 없애줌
parseInt(string)
▶ 전달 받은 문자열을 정수로 해석하여 반환
▷ 2번째 인수로 진법을 나타내는 기수를 전달 가능 (2~36)
▷ 10진수 형태로 반환
// 10'을 10진수로 해석하고 그 결과를 10진수 정수로 반환한다
parseInt('10'); // -> 10
// '10'을 2진수로 해석하고 그 결과를 10진수 정수로 반환한다
parseInt('10', 2); // -> 2
// '10'을 8진수로 해석하고 그 결과를 10진수 정수로 반환한다
parseInt('10', 8); // -> 8
// '10'을 16진수로 해석하고 그 결과를 10진수 정수로 반환한다
parseInt('10', 16); // -> 16
▶ toString(number) : 기수를 지정하여 10진수 숫자를 해당 기수의 문자열로 변환
const x = 15;
// 10진수 15를 2진수로 변환하여 그 결과를 문자열로 반환한다.
x.toString(2); // -> '1111'
// 문자열 '1111'을 2진수로 해석하고 그 결과를 10진수 정수로 반환한다
parseInt(x.toString(2), 2); // -> 15
// 10진수 15를 8진수로 변환하여 그 결과를 문자열로 반환한다.
x.toString(8); // -> '17'
// 문자열 '17'을 8진수로 해석하고 그 결과를 10진수 정수로 반환한다
parseInt(x.toString(8), 8); // -> 15
// 10진수 15를 16진수로 변환하여 그 결과를 문자열로 반환한다.
x.toString(16); // -> 'f'
// 문자열 'f'를 16진수로 해석하고 그 결과를 10진수 정수로 반환한다
parseInt(x.toString(8), 8); // -> 15
// 숫자값을 문자열로 변환한다.
x.toString(); // -> '15'
// 문자열 '15'를 10진수로 해석하고 그 결과를 10진수 정수로 반환한다
parseInt(x.toString()); // -> 15
▶ 16진수 리터럴 (ex: 0xf) 의 경우 해석 가능
▶ 숫자로 변환할 수 없으면 NaN 반환
▶ 앞뒤 공백을 없애줌
▶ 2번째 인수로 기수를 전달한 경우, 해당 진수로 해석할 수 없는 부분부터는 무시
// 10진수로 해석할 수 없는 'A' 이후의 문자는 모두 무시된다.
parseInt('1A0'); // -> 1
// 2진수로 해석할 수 없는 '2' 이후의 문자는 모두 무시된다.
parseInt('102', 2); // -> 2
// 8진수로 해석할 수 없는 '8' 이후의 문자는 모두 무시된다.
parseInt('58', 8); // -> 5
// 16진수로 해석할 수 없는 'G' 이후의 문자는 모두 무시된다.
parseInt('FG', 16); // -> 15
encodeURI / decodeURI
▶ encodeURI
▷ 완전한 URI를 문자열로 전달받아 이스케이프 처리를 위해 인코딩
▷ 예를 들어 URI에 한글이 섞여 있으면 %6EF4VF ~ 처럼 변환이 필요한데 이것을 수행
▶ decodeURI
▷ 인코딩된 URI를 인수로 전달받아 이스케이프 처리 이전으로 디코딩
const uri = 'http://www.naver.com?name=김종한&job=frontend';
// encodeURI 함수는 완전한 URI를 전달받아 이스케이프 처리를 위해 인코딩한다.
const enc = encodeURI(uri);
console.log(enc);
// http://www.naver.com?name=%EA%B9%80%EC%A2%85%ED%95%9C&job=frontend
conet dec = decodeURI(enc);
console.log(dec); // 'http://www.naver.com?name=김종한&job=frontend';
encodeURIComponent / decodeURIComponent
▶ encodeURIComponent
▶ encodeURI 와 다른 점은, 쿼리스트링 구분자로 사용되는 ?, =, & 까지 인코딩한다
// URI의 쿼리 스트링
const uriComp = 'name=김종한&job=programmer&teacher';
// encodeURIComponent 함수는 인수로 전달받은 문자열을 URI의 구성요소인 쿼리 스트링의 일부로 간주한다.
// 따라서 쿼리 스트링 구분자로 사용되는 =, ?, &까지 인코딩한다.
let enc = encodeURIComponent(uriComp);
console.log(enc);
// name%3D%EC%9D%B4%EC%9B%85%EB%AA%A8%26job%3Dprogrammer%26teacher
let dec = decodeURIComponent(enc);
console.log(dec);
// 김종한&job=programmer&teacher
// encodeURI 함수는 인수로 전달받은 문자열을 완전한 URI로 간주한다.
// 따라서 쿼리 스트링 구분자로 사용되는 =, ?, &를 인코딩하지 않는다.
enc = encodeURI(uriComp);
console.log(enc);
// name=%EC%9D%B4%EC%9B%85%EB%AA%A8&job=programmer&teacher
dec = decodeURI(enc);
console.log(dec);
// name=김종한&job=programmer&teacher