[제로초님의 중요 개념 요약](https://www.youtube.com/watch?v=RdbVLzAfB44&t=276s)
1~15장 다읽기 16장 안읽어도 됨 17장 몰라도 지장은 없는데 알면 좋음 18,19 읽어 20 몰라도됨 21장 읽어 22장 꼭알아야햄 23 젤중요함 -여러번 읽어 24,25,26,27 읽어(배열메소드는 알아두면 효율 높아짐) - 읽어 28,29,30장 - 필요할때 그때 그떄 봐 31 - 몰라도 지장은 없는데 알면 좋음 32- 그때그때 찾아보면 됨 33 - 심볼 : 메타데이터 용인데. 초보자들은 왜 쓰는지 모를 수 있음반반 34 이터러블 반반 - 잘쓰는 사람은 잘쓰고 모르는 사람은 안씀 35,36 알아야함 37 알면 좋음 38,39- 프론트라면 꼭 알아야함 40 알아야함 41 알아야함 42 알아야함 43,44 쭉 보면 됨 45 프로미스 중요 46 몰라도 됨 47 중요 48 매우 중요 49 프론트는 꼭 알아야함
Untitled
독서 계획
- 총 917쪽
- 예상 기간 : 8주
- 소스코드
1회독 당시 읽은 내용
요약
- jQuery
- DOM을 더욱 쉽게 제어, 크로스 브라우징 이슈 해결
- V8 JS 엔진
- 웹 애플리케이션의 기능 ; UX(User Experience) 제공
- Node.js
- 구글 V8 JS엔진으로 빌드된 JS 런타임 환경
- JS엔진을 브라우저에서 독립시킨 JS 실행 환경
- 비동기 I/O 지원, 단일 스레드 이벤트 루프 기반으로 동작
- NPM ; Node Package Manager
- JS 패키지 매니저
- Node.js에서 사용할 수 있는 모듈들을 패키지화해서 모아둔 저장소 역할
- 패키지 설치 및 관리를 위한 CLI 제공
- SPA 프레임워크
- ex) Angular,React,Vue,Svelte
- JS 특징
- 웹 브라우저에서 동작하는 유일한 프로그래밍 언어
- 인터프리터 언어
- 멀티 패러다임 프로그래밍 언어 ; 명령형, 함수형, 프로토타입 기반, 객체지향 프로그래밍 지원
- 변수의 호이스팅 ; var, let, const, function, function*, class 모두 호이스팅 됨
- var은 호이스팅되며 undefined로 초기화 되지만, 그 외의 것들은 초기화 x
- 변수 선언 ; 런타임 이전에 먼저 실행 → 값의 할당 ; 런타임에 실행
- 런타임 ; 소스코드가 순차적으로 실행되는 시점
- 매니지드 언어 ; 메모리 관리 기능을 언어 차원에서 담당하고 개발자의 직접적인 메모리 제어를 허용하지 않음
- 동적 타이핑 ; 변수가 선언이 아닌 할당에 의해 타입이 결정
변수
- 값 ; 식이 평가되어 생성된 결과
- 리터럴 ; 사람이 이해할 수 있는 문자 또는 약속된 기호를 사용해 값을 생성하는 표기법
- ex) 정수 리터럴, 2진수 리터럴, null 리터럴, 객체 리터럴, 배열 리터럴 ..
- 표현식 ; 값으로 평가될 수 있는 문
- ex) 리터럴 표현식, 식별자 표현식, 연산자 표현식, 함수/메서드 호출 표현식 ..
- 문 ; 프로그램을 구성하는 기본단위이자 최소 실행 단위
- 문의 집합으로 이루어진 것이 프로그램
- 여러 토큰으로 구성
데이터 타입
원시 타입(Primitive Type)
💡 (값을) 변경 불가능한 값
- 변수에 할당 시 실제 값이 저장
- 다른 변수에 할당 시 원시 값이 복사되어 전달
- 원시 값을 할당한 변수에 새로운 원시 값을 재할당 → 새로운 메모리 공간을 확보하고 재할당한 원시 값을 저장한 후, 변수는 새롭게 재할당한 원시 값을 가리킴
- 두 변수의 원시 값은 서로 다른 메모리 공간에 저장된 별개의 값이 되어 어느 한쪽에서 재할당을 통해 값을 변경하더라도 서로 간섭할 수 없음
1. 숫자
- 모든 수를 실수 처리 → 정수끼리 나누더라도 실수가 나옴
- 특별한 값 ; Infinity, -Infinity, NaN
2. 문자열
- 1개의 문자는 2Byte의 메모리 공간에 저장
- 변경 불가
- 유사 배열객체이면서 이터러블이므로 배열과 유사하게 각 문자에 접근 가능
- but 일부 문자를 변경해도 반영 x ; 문자열은 변경 불가능한 값이기 때문
- 템플릿 리터럴(
)- 줄바꿈 허용
- 이스케이프 시퀀스
- \0 ; Null, \b ; 백스페이스, \n ; 다음 행, \r ; 커서를 처음으로 이동, \t ; 탭, \v ; 탭(수직)
3. Bool
; T/F
4. undefined
; 개발자가 의도적으로 할당한 값 x, JS 엔진이 변수를 초기화할 때 사용하는 값
5. null ; 변수에 값이 없다는 것을 의도적으로 명시할 때 사용
- typeof null = object ; JS의 고치지 못한 오류임. 유의할 것. 일치 연산자로 확인하기
- 심벌 ; 변경 불가능한 원시 타입의 값
- 다른 값과 중복되지 않는 유일무이한 값
- 이름이 충돌할 위험이 없는 객체의 유일한 프로퍼티 키를 만들기 위해 사용
- Symbol 함수를 호출해 생성
객체 타입(Reference, Object Type)
💡 변경 가능한 값
- 변수에 할당 시 참조 값이 저장
- 다른 변수에 할당 시 참조 값이 복사되어 전달
- const 키워드를 사용해 사용한 변수에 할당한 객체는 변경 가능
- 생성된 객체가 실제로 저장된 메모리 공간의 주소가 저장
- 얕은 복사와 깊은 복사
- 얕은 복사 ; 한 단계까지만 복사, 객체에 중첩되어 있는 객체의 경우 참조값을 복사
- ex) 스프레드 복사
- 얕은 복사 ; 한 단계까지만 복사, 객체에 중첩되어 있는 객체의 경우 참조값을 복사
- 깊은 복사 ; 객체에 중첩되어있는 객체까지 모두 복사, 객체에 중첩되어 있는 객체까지 모두 복사
- ex) _.cloneDeep()
1. 객체 ; 프로퍼티와 메소드로 구성된 집합체
let person = {
name:'Lee',
age:20
};
- 프로퍼티 키 ; 문자열 또는 심벌 값
- 프로퍼티 값에 접근할 수 있는 이름
- 식별자 네이밍 규칙을 준수한다면 따옴표 생략해도 됨 / 준수 x → 대괄호로 묶어야함
네이밍 규칙
- 반드시 문자로 시작 - 1~30까지만 지정 가능 - A~Z까지의 대소문자, 0~9까지의 숫자, 특수기호는 _, $, #만 가능 - 오라클에서 사용되는 예약어 사용 불가 - 다른 객체명에서 사용중인 것과 중복 불가 - 공백 사용 불가- 프로퍼티 값
- JS에서 사용할 수 있는모든 값
- 프로퍼티 ; 객체의 상태를 나타내는 값
- 프로퍼티 생성 ; 프로퍼티에 값을 할당하면 동적 생성되어 추가됨
person.age=20- 대괄호를 사용하여 동적 생성도 가능
obj[${나이}-${++age}]:i,
- 대괄호를 사용하여 동적 생성도 가능
- 프로퍼티 생성 ; 프로퍼티에 값을 할당하면 동적 생성되어 추가됨
- 프로퍼티 삭제 ; delete 연산자 사용
delete person.age
- 메서드 ; 프로퍼티를 참조하고 조작할 수 있는 동작
- 객체 리터럴은 값으로 평가되는 표현식이기에 객체 리터럴의 닫는 중괄호 뒤에는 세미콜론이 붙음
2. 함수 ; 입력을 받아 출력을 내보내는 일련의 과정을 정의한 것
- JS의 일급 객체
- 매개변수 ; 함수 내부로 입력을 전달받는 변수
- 가급적 적게 만드는 것이 좋음, 3개 이상 넘지 않는 것을 권장
- 인수 ; 입력
- 함수를 호출할 때 지정
- 모든 인수는 암묵적으로 arguments 객체의 프로퍼티로 보관
- 인수가 전달되지 않은 경우 단축 평가, 매개변수의 기본값를 통해 매개변수에 기본값 할당
- 반환값 ; 출력
- 모든 값을 반환 가능
- 함수의 실행 중단 & return 키워드 뒤에 오는 표현식을 평가해 반환
- 함수 선언문
function add(x,y) { return x+ y; }- 함수 표현식 이전에 호출 가능
- 함수 표현식
var add = function(x,y) { return x+y; };- 함수 표현식 이전에 호출 불가능
- 생성자 함수
var add = new Function('x','y','return x + y'); - 화살표 함수
const add = (x,y) ⇒ x+y;- 항상 익명 함수로 정의
- 즉시 실행 함수 ; 함수 정의와 동시에 즉시 호출되는 함수
- 재귀 함수 ; 함수가 자신을 호출하는 함수
- 중첩 함수 ; 함수 내부에 정의 된 함수
- 콜백 함수 ; 함수의 매개변수를 통해 다른 함수의 내부로 전달되는 함수
- 비동기 처리(이벤트처리, Ajax 통신, 타이머 함수 등)에 활용
- 고차 함수 ; 매개변수를 통해 함수의 외부에서 콜백 함수를 전달받은 함수
- reduce, filter, map 안에 들어 가는 콜백 함수
- 순수 함수와 비순수 함수
- 순수 함수 ; 어떤 외부 상태에 의존하지 않고 변경하지도 않는 함수
- 함수의 외부 상태 변경 x ⇒ 권장
- 순수 함수 ; 어떤 외부 상태에 의존하지 않고 변경하지도 않는 함수
- 비순수 함수 ; 외부 상태에 의존하거나 외부 상태를 변경하는 함수
- 함수의 외부 상태를 변경하는 부수효과 O
3. 배열
동등 비교와 일치 비교
동등 비교(==)
; x와 y의 값이 같은지 비교, 예측하기 힘들기에 사용하지 않는 것 권장
- ex) 5==’5’ ; true
일치 비교(===)
; x와 y의 값이 같고, 타입도 같은지 비교
- 특수상황 ; NaN === NaN ⇒ false
- Number.isNaN(NaN) ⇒ True
쉼표 연산자
; 왼쪽 피연산자부터 차례대로 피연산자를 평가하고 마지막 피연산자의 평가가 끝나면 마지막 피연산자의 평가 결과를 반환
var x,y,z;
x=1,y=2,z=3; //3 return
break문 ; 레이블 문, 반복문(for,for…in,for…of,while,do…while),switch문의 코드블록 탈출continue문 ; 반복문의 코드 블록 실행을 현 지점에서 중단하고 반복문의 증감식으로 실행 흐름을 이동시킴
타입 변환
1. 문자열
; 피연산자 중 하나 이상이 문자열이면 문자열 연결 연산자로 동작
- 암묵적
- 숫자, Bool, null, undefined, Object
+ " "
- 숫자, Bool, null, undefined, Object
- 명시적
String( ), .toString( )
2. 숫자
; 산술 연산자의 피연산자 중 숫자 타입이 아닌 피연산자를 숫자 타입으로 암묵적 타입 변환
- 암묵적
+문자열, Bool, null, 빈 배열 / * 1
- 명시적
Number( ),parseInt( ),parseFloat( )
3. Bool
- 암묵적
- false로 평가되는 값 ;
false,undefined,null,0,-0,NaN,' '→ 그 외 ; true
- false로 평가되는 값 ;
- 명시적
Boolean( ),!!
단축 평가
논리곱 연산자
; 논리 연산의 결과를 결정한 두 번째 피연산자 반환
-
ex)
A && B -
A가 참이면 B 반환, A가 거짓이면 false 반환
let elem = null; let value = elem && elem.value;- elem이 Falsy값이면 elem으로 평가되고, elem이 Truthy 값이면 elem.value로 평가됨
논리합 연산자
; 논리 연산의 결과를 결정한 첫 번째 피연산자 반환
-
ex)
A || B -
A가 참이면 A 반환, A가 거짓이면 B 반환
-
AB 모두 참이면 A반환, A만 참이면 A반환, B만 참이면 B반환, AB 모두 거짓이면 false 반환
const func = (str) =>{ str = str || ''; return str.length; }- str이 Falsy값이면 0반환(’’가 들어감), Truthy값이면 str의 길이 반환
옵셔널 체이닝 연산자
; 좌항의 피연산자가 null 또는 undefined이면 undefined 반환, Truthy이면 프로퍼티 우항의 참조 이어감
- ex)
let value = elem?.value; 변수가 null 또는 undefined가 아닌지 확인하고 프로퍼티를 참조할 때 유용 - 논리연산자 &&을 사용할 때 좌항의 피연산자가 Falsy이면 좌항 피연산자 그대로 반환 → 0이나 ‘’도 해당되는 단점 보완
null 병합 연산자
; 좌항의 피연산자가 null 또는 undefined의 경우 우항의 피연산자를 반환하고, 그렇지 않으면 좌항의 피연산자 반환
- ex)
let foo = null ?? ‘default String’; 변수에 기본값 설정할 때 유용 - 논리연산자 ||를 사용할 때 좌항의 피연산자가 Falsy이면 우항의 피연산자 반환 → 0이나 ‘’도 기본값으로서 유효하다면 예기치 않은 동작 발생한다는 단점 보완
용어 정리
- 웹 크롤링 ; 서버에서 웹사이트의 콘텐츠를 수집하기 위해 웹사이트에서 HTML 문서를 가져온 다음, 이를 가공해서 필요한 데이터만 추출하는 것
- 컴파일러, 인터프리터 ; 컴퓨터가 이해할 수 있는 기계어로 변환하는 일종의 번역기
- 프로그래밍 ; 요구사항의 집합을 분석해서 적절한 자료구조와 함수의 집합으로 변환한 후, 그 흐름을 제어하는 것
- Ajax(Asynchronous JavaScript and XML) ; JS를 이용해 비동기 방식으로 데이터를 교환할 수 있는 통신 기능
- Ajax의 등장으로 서버로부터 필요한 데이터만 전송받아 변경해야하는 부분만 한정적으로 렌더링하는 방식이 가능
- 렌더링 ; HTML,CSS,JS로 작성된 문서를 해석해서 브라우저에 시각적으로 출력하는 것
- 호이스팅 ; 변수 선언문이 코드의 선두로 끌어 올려진 것처럼 동작하는 것
- 변수 선언이 소스코드의 어디에 위치하는지와 상관없이 어디서든지 변수를 참조할 수 있음
- 토큰 ; 문법적인 의미를 가지며, 문법적으로 더 이상 나눌 수 없는 코드의 기본 요소
스코프
; 자신이 선언된 위치에 의해 다른 코드가 식별자(변수 이름, 함수 이름, 클래스 이름 등)를 참조할 수 있는 유효범위
- 전역 변수와 지역 변수
- 전역 변수 ; 어디서든지 참조 가능
- 지역 변수 ; 자신의 지역 스코프와 하위 지역 스코프에서 유효
- 동적 스코프 ; 함수를 어디서 호출했는지에 따라 함수의 상위 스코프 결정
- 레시컬 스코프 ; 함수를 어디서 정의했느냐에 따라 함수의 상위 스코프 결정
- JS를 비롯한 대부분의 프로그래밍 언어가 채택
- var, let, const의 차이점
- var ; 함수의 코드 블록만을 지역 스코프로 인정
- 선언+초기화 > 할당
- var ; 함수의 코드 블록만을 지역 스코프로 인정
- let ; 모든 코드블록(함수, if문, for문, while문, try/catch문 등)을 지역스코프로 인정
- 선언 > 초기화 > 할당
- const ; 선언과 동시에 초기화해야 함
- 변경이 불가한 것이 아니라, “재할당”이 불가임
- 즉, 프로퍼티 동적 생성, 삭제, 프로퍼티 값의 변경을 통한 객체 변경은 가능
- let, const를 포함해서 모든 선언(var, let, const, function, fuction*, class 등)을 호이스팅
- 단, let, const, class를 사용한 선언문은 호이스팅이 발생하지 않는 것처럼 동작
💡 기본적으로 const 사용, let은 재할당이 필요한 경우에 한정해 사용할 것
프로퍼티 어트리뷰트
- 내부 슬롯 = 의사 프로퍼티, 내부 메소드 = 의사 메소드, 이중 대괄호([[ … ]])로 감쌈
- 데이터 프로퍼티 ; 키와 값으로 구성된 일반적인 프로퍼티
- 프로퍼티 어트리뷰트 ; value(프로퍼티의 값), writable(값의 갱신 가능 여부), enumerable(열거 가능 여부), configurable(재정의 가능 여부)
- 접근자 프로퍼티 ; 자체적으로 값을 가지지 않고 다른 데이터 프로퍼티의 값을 읽거나 저장할 때 호출되는 접근자 함수로 구성된 프로퍼티
- 프로퍼티 어트리뷰트 ; get(접근자 프로퍼티 키로 프로퍼티 값에 접근할 때), set(접근자 프로퍼티를 통해 데이터 프로퍼티의 값을 저장할 때 호출), enumerable, configurable
- 프로퍼티 확인 ;
Object.getOwnPropertyDescriptor(객체 명, 프로퍼티 명)메서드 사용하여 간접 확인
const person = {
// 데이터 프로퍼티
firstName: "Park",
lastName: "guesung",
// 접근자 함수로 구성된 접근자 프로퍼티
// getter 함수
get fullName() {
return `${this.firstName} ${this.lastName}`;
},
// setter 함수
set fullName(name) {
// 배열 구조분해 할당
[this.firstName, this.lastName] = name.split(" ");
},
};
//
데이터 프로퍼티
를 통한 프로퍼티 값의 참조
console.log(person.firstName + " " + person.lastName); // Park Guesung
//
접근자 프로퍼티
를 통한 프로퍼티 값의 저장
// 접근자 프로퍼티
fullName에 값을 저장하면
setter 함수가 호출
된다.
person.fullName = "Heegun Lee";
console.log(person); // {firstName: "Heegun", lastName: "Lee"}
// 접근자 프로퍼티를 통한 프로퍼티 값의 참조
// 접근자 프로퍼티
fullName에 접근하면
getter 함수가 호출된다
.
console.log(person.fullName); // Heegun Lee
// firstName은 데이터 프로퍼 티
// 데이터 프로퍼티는 [[Value]], [[Writable]], [[Enumerable]], [[Configurable]] 프로퍼티 어트리뷰트를 갖는다.
let descriptor = Object.getOwnPropertyDescriptor(person, "firstName");
console.log(descriptor);
// {value: "Heegun", writable: true, enumerable: true, configurable: true}
// fullName은 접근자 프로퍼티
// 접근자 프로퍼티는 [[Get]], [[Set]], [[Enumerable]], [[Configurable]] 프로퍼티 어트리뷰트를 갖는다.
descriptor = Object.getOwnPropertyDescriptor(person, "fullName");
console.log(descriptor);
// {get: ƒ, set: ƒ, enumerable: true, configurable: true}
// 일반 객체의 __proto__는 접근자 프로퍼티
Object.getOwnPropertyDescriptor(Object.prototype, '__proto__');
// {get: ƒ, set: ƒ, enumerable: false, configurable: true}
// 함수 객체의 prototype은 데이터 프로퍼티
Object.getOwnPropertyDescriptor(function() {}, 'prototype');
// {value: {...}, writable: true, enumerable: false, configurable: false}
- 프로토타입 ; 어떤 객체의 상위 객체의 역할을 하는 객체
- 하위 객체에게 자신의 프로퍼티와 메서드를 상속
- 프로토타입 체인 ; 프로토타입이 단방향 링크드 리스트 형태로 연결되어 있는 상속 구조
- 프로퍼티 정의 ;
Object.defineProperty메소드 사용하여 프로퍼티 어트리뷰트 정의- 기본값
- value,get,set ; undefined / writable, enumerable, configurable ; false
- 기본값
const person = {};
// 데이터 프로퍼티 정의
Object.defineProperty(person, 'firstName', {
value: 'Ungmo',
writable: true,
enumerable: true,
configurable: true
});
Object.defineProperty(person, 'lastName', {
value: 'Lee'
});
let descriptor = Object.getOwnPropertyDescriptor(person, 'firstName');
console.log('firstName', descriptor);
// firstName {value: "Ungmo", writable: true, enumerable: true, configurable: true}
// 디스크립터 객체의 프로퍼티를 누락시키면
undefined, false가 기본값
descriptor = Object.getOwnPropertyDescriptor(person, 'lastName');
console.log('lastName', descriptor);
// lastName {value: "Lee", writable: false, enumerable: false, configurable: false}
// 접근자 프로퍼티 정의
Object.defineProperty(person, 'fullName', {
// getter 함수
get() {
return `${this.firstName} ${this.lastName}`;
},
// setter 함수
set(name) {
[this.firstName, this.lastName] = name.split(' ');
},
enumerable: true,
configurable: true
});
descriptor = Object.getOwnPropertyDescriptor(person, 'fullName');
console.log('fullName', descriptor);
// fullName {get: ƒ, set: ƒ, enumerable: true, configurable: true}
person.fullName = 'Heegun Lee';
console.log(person); // {firstName: "Heegun", lastName: "Lee"}
- 객체 변경 방지
- 확장 금지 ;
Object.preventExtensions(object),Object.isExtensible(object)- 추가만 금지
- 확장 금지 ;
- 밀봉 금지 ;
Obejct.seal(object),Object.isSealed(object)- 읽기 & 쓰기만 허용
- 동결 ;
Object.freeze(object),Object.isFrozen(object)- 읽기만 허용
생성자 함수에 의한 객체 생성
-
생성자 함수 ; new 연산자와 함께 호출하여 객체(인스턴스)를 생성하는 함수
-
인스턴스 ; 생성자 함수에 의해 생성된 객체
- 빌트인 생성자 함수 ; String, Number, Boolean, Function, Array, Date, RegExp, Promise 등
-
장점 ; 프로퍼티 구조가 동일한 객체 여러 개를 간편하게 생성 가능
// 생성자 함수 function Circle(radius) { // 생성자 함수 내부의 this는 생성자 함수가 생성할 인스턴스를 가리킨다. this.radius = radius; this.getDiameter = function () { return 2 * this.radius; }; } // 인스턴스의 생성 const circle1 = new Circle(5) ; // 반지름이 5인 Circle 객체를 생성 const circle2 = new Circle(10) ; // 반지름이 10인 Circle 객체를 생성 console.log(circle1.getDiameter()); // 10 console.log(circle2.getDiameter()); // 20 -
this ; 객체 자신의 프로퍼티나 메서드를 참조하기 위한 자기 참조 변수
-
인스턴스 생성 과정
- 인스턴스 생성과 this 바인딩
- 인스턴스 초기화
- 인스턴스에 프로퍼티나 메서드 추가, 생성자 함수가 인수로 잔달받은 초기값을 프로퍼티에 할당하여 초기화하거나 고정값 할당
- 인스턴스 반환
- 완성된 인스턴스가 바인딩된 this가 암묵적으로 반환
- 생성자 함수 내부에서 return문 생략해야 함
- [[call]]과 [[construct]]
- 함수가 일반함수로서 호출되면 함수 객체의 내부 메서드 [[call]]호출
- this는 전역 객체 window 가리킴
- 함수가 일반함수로서 호출되면 함수 객체의 내부 메서드 [[call]]호출
- new 연산자와 함께 생성자 함수로서 호출되면 내부 메서드 [[construct]]호출
- this는 생성자 함수가 생성할 인스턴스 가리킴
- constructor와 non-constructor
- cunstructor ; 함수 선언문, 함수 표현식, 클래스
- non-constructor ; 메서드, 화살표 함수
- new로 생성 불가
- new.target
- 생성자함수 ; 함수 자신을 가리킴
- 일반 함수 ; undefined
- new.target을 이용하여 생성자 함수로서 호출했는지 확인하여 그렇지 않은경우 new 연산자와 함께 재귀 호출을 통해 생성자 함수로서 호출 가능
// 생성자 함수
function Circle(radius) {
// 이 함수가 new 연산자와 함께 호출되지 않았다면 new.target은 undefined다.
if (!new.target) {
// new 연산자와 함께 생성자 함수를 재귀 호출하여 생성된 인스턴스를 반환한다.
return new Circle(radius);
}
this.radius = radius;
this.getDiameter = function () {
return 2 * this.radius;
};
}
// new 연산자 없이 생성자 함수를 호출하여도 new.target을 통해 생성자 함수로서 호출된다.
const circle = Circle(5);
console.log(circle.getDiameter());
일급 객체
; 무명의 리터럴로 생성 가능 + 변수나 자료구조(객체, 배열)에 저장 가능 + 함수의 매개변수에 전달 가능 + 함수의 반환값으로 사용 가능
- JS 함수는 위의 조건을 만족하므로 일급 객체임
- 일급 객체 ; 함수를 객체와 동일하게 사용할 수 있다
- 함수 객체의 프로퍼티
- arguments 프로퍼티
- 함수 호출 시 전달된 인수들의 정보를 담고 있음
- arguments 프로퍼티
- 순회 가능한 유사 배열 객체
- 함수 내부에서 지역 변수처럼 사용 가능
- ES6에서 Rest파라미터 도입 이후 잘 안씀
- caller 프로퍼티 ; 잘 안씀
- length 프로퍼티 ; 함수를 정의할 떄 선언한 매개변수의 개수
function foo(x,y){
return x*y;
}
console.log(foo.length()); //2
- name 프로퍼티 ; 함수 객체를 가리키는 식별자를 값으로 가짐
- proto 접근자 프로퍼티 ; 내부 슬롯이 가리키는 프로토타입 객체에 접근하기 위해 사용하는 접근자 프로퍼티
- prototype 프로퍼티 ; 생성자 함수로 호출할 수 있는 함수 객체
프로토타입
- JS의 원시 타입을 제외한 나머지 값들(함수,배열,정규 표현식 등)은 모두 객체
- 객체의 상태 데이터 ; 프로퍼티 / 객체의 동작 ; 메서드
- 상속 ; 어떤 객체의 프로퍼티 또는 메서드를 다른 객체가 상속받아 그대로 사용할 수 있는 것
// 생성자 함수
function Circle(radius) {
this.radius = radius;
}
// Circle 생성자 함수가 생성한 모든 인스턴스가
getArea 메서드를
//
공유해서 사용할 수 있도록 프로토타입에 추가
한다.
// 프로토타입은 Circle 생성자 함수의 prototype 프로퍼티에 바인딩되어 있다.
Circle.prototype.getArea
= function () {
return Math.PI * this.radius ** 2;
};
// 인스턴스 생성
const circle1 = new Circle(1);
const circle2 = new Circle(2);
// Circle 생성자 함수가 생성한 모든 인스턴스는 부모 객체의 역할을 하는
// 프로토타입 Circle.prototype으로부터 getArea 메서드를 상속받는다.
// 즉, Circle 생성자 함수가 생성하는 모든 인스턴스는 하나의 getArea 메서드를 공유한다.
console.log(circle1.getArea === circle2.getArea); // true
console.log(circle1.getArea()); // 3.141592653589793
console.log(circle2.getArea()); // 12.566370614359172
- 객체가 생성될 때 객체 생성 방식에 따라 프로토타입이 결정됨 &
[[prototype]]에 저장 됨 - 모든 객체는 하나의 프로토타입을 가짐
- 모든 프로토타입은 생성자 함수와 연결되어 있음
- proto 접근자 프로퍼티 ; 자신의 프로토타입, 즉 [[prototype]] 내부 슬롯에 간접적으로 접근 가능
- name:”Lee” ; person객체의 프로퍼티
- [[prototype]] ; person객체의 프로토타입
Strict mode
; JS언어의 문법을 좀 더 엄격히 적용하여 오류를 발생시킬 가능성이 높거나 JS엔진의 최적화 작업에 문제를 일으킬 수 있는 코드에 대해 명시적인 에러를 발생시킴
'use strict';
function foo(){
x = 10; //ReferenceError:x is not defined
}
foo();
빌트인 객체
1. 표준 빌트인 객체
; ECMAScript 사양에 정의된 객체, 애플리케이션 전역의 공통 기능 제공
- Object,String,Number,Boolean,Symbol,Date,RegExp,Array 등 40여 개 존재
- Math,Reflect,JSON제외한 모두 인스턴스를 생성할 수 있는 생성자 함수 객체
- 생성자함수인 표준 빌트인 객체가 생성한 인스턴스의 프로토타입은 표준 빌트인 객체의 prototype 프로퍼티에 바인딩된 객체
const strObj = new String('Lee');
console.log(Object.getPrototypeOf(StrObj) === String.prototype); // true
- 원시값은 객체가 아니므로 프로퍼티나 메서드를 가질 수 없는데도 원시값인 문자열이 마치 객체처럼 동작
str.length,str.toUpperCase();
- 래퍼 객체 ; 이처럼 문자열, 숫자, 불리언 값에 대해 객체처럼 접근하면 생성되는 임시 객체
- 전역 객체 ; 코드가 실행되기 이전 단계에 js엔진에 의해 어던 객체보다도 먼저 생성되는 특수하 객체
- 브라우저 환경 ; window(혹은 self,this,frames) / Node.js환경 ; global(혹은 this)
- 빌트인 전역 프로퍼티
Infinity; 무한대 /NaN; 숫자가 아님 /undefined
- 빌트인 전역 함수
eval(); ()안의 식 실행 but 처리 속도가 느리기에 사용 금지
isFinite(); 유한수인지 검사 /isNaN(); NaN인지 검사parseFloat(); 실수로 해석하여 반환parseInt(num,x); 정수로 해석 하여 반환- x진수 → 10진수로 변환 (2~36진수)
- 해당 지수의 숫자로 변환할 수 없다면 NaN 반환
- 그 반대 ;
num.toString(x)- 10진수 → x진수로 변환
- string형으로 반환
- encodeURI ; 완전한 URI를 문자열로 전달받아 이스케이프 처리를 위해 인코딩
- decodeURI ; 인코딩된 URI를 인수로 전달받아 이스케이프 처리 이전으로 디코딩
- encodeURIComponent ; URI 구성 요소를 인수로 전달받아 인코딩
- 쿼리 스트링 구분자로 사용되는 =,?,&까지 인코딩
- decodeURIComponent ; 매개변수로 전달된 URI 구성 요소를 디코딩
2. 호스트 객체
; ECMAScript 사양에 정의되어 있지 않지만 JS 실행 환경에서 추가로 제공하는 객체
3. 사용자 정의 객체
; 사용자가 직접 정의한 객체
this
; 자신이 속한 객체 또는 자신이 생성할 인스턴스를 가리키는 자기 참조 변수
- 일반 함수 내의 this ; 전역 객체 window 가리킴
square(1); - 메서드 내의 this ; 메서드를 호출한 객체 가리킴
const person={getName(){ }} - 생성자 함수 내의 this ; 생성자 함수가 생성할 인스턴스 가리킴
const a = new Square(1); - Function.prototype.apply/call/bind메서드에 의한 간접 호출
TIP
- 변수
- 변수의 무분별한 남발은 금물, 필요한 만큼 최소한으로 유지하도록 주의
- 변수의 스코프는 최대한 좁게 만들어 변수의 부작용 억제
- 전역 변수는 최대한 지양
- 변수보다는 상수를 사용해 값의 변경 억제
- 변수의 목적이나 의미를 파악할 수 있도록 네이밍
요약
0. Intro
기본 개념과 동작 원리 > 코딩 기술 > 프로젝트. 3개의 사이클을 순환적으로 반복하면서 이해의 반경을 점진적으로 넓혀가는 것, 즉 지속적 개선을 통한 성장이 바로 학습이다.
자신의 능력으로 쉽게 해결 가능한 것을 반복하는 것, 라이브 코딩을 감상하거나 예제를 단순히 타이핑하는 것은 연습이 아닙니다. 자신의 능력을 살짝 넘어서는 도전을 지속적으로 시도하는 것이 의도적인 연습입니다.
1. 프로그래밍이란?
- 프로그래밍 : 컴퓨터에게 요구하는 일종의 커뮤니케이션
- 정확하고 상세하게 요구사항을 설명하는 작업
- 요구사항의 집합을 분석해서 적절한 자료구조와 함수의 집합으로 변환한 후, 그 흐름을 제어하는 것
2. 자바스크립트란?
1) 자바스크립트의 탄생
- 초기 이름 : 모카
- 그 이후 라이브 스크립트 > 자바스크립트로 최종 명명(1996년)
2) 자바스크립트의 표준화
-
크로스 브라우징 이슈
컴퓨터 시스템의 표준을 관리하는 비영리 표준화기구인 ECMA인터네셔널은 자바스크립트의 표준화를 위해 ECMAScript 사양을 만들었다.
ES6(ECMAScript 2015)에서 let/const, 클래스 등 다양한 문법이 등장했다.
3) 자바스크립트의 성장
- AJAX : 비동기 통신
- jQuery : DOM을 쉽게 제어
- V8 자바스크립트 엔진 : 데스크톱 애플리케이션과 유사한 사용자 경험을 제공할 수 있는 웹 애플리케이션 언어로 정착
- Node.js : 구글 V8자바스크립트 엔진으로 빌드된 자바스크립트 런타임
- 자바스크립트 엔진을 브라우저에서 독립시킨 자바스크립트 실행환경
- 비동기 I/O을 지원하며 단일 스레드 이벤트 루프 기반으로 동작하여 요청처리 선응이 좋다.
- SPA 프레임워크 : Angular, React, Vue, Svelte 등 SPA 프레임워크/라이브러리 등 등장
4) 자바스크립트와 ECMAScript
ECMAScript는 자바스크립트의 표준 사양인 ECMA-262를 말하며, 프로그래밍 언어의 값, 타입, 객체와 프로퍼티 등 핵심 문법을 규정한다.
자바스크립트는 일반적으로 프로그래밍 언어로서 기본 뼈대를 이루는 ECMAScript와 브라우저가 별도 지원하는 클라이언트 사이드 WEB API(DOM, BOM, Canvas ..)등을 아우르는 개념을 말한다. Web API는 ECMAScript와 별도로 월드 와이드 웹 콘소시옴에서 별도의 사양으로 관리하고 있다
5) 자바스크립트 특징
- 웹 브라우저에서 동작하는 유일한 프로그래밍 언어
- 인터프리터 언어
- 인터프리터 언어의 장점인 동적 기능 지원
- 인터프리터 언어의 단점인 실행 속도가 느리다는 점을 살리기 위해 컴파일을 일부 도입하였다. 하지만 런타임 중에 컴파일을 하고, 실행 파일이 생성되지 않기에 컴파일러 언어라 할 수 없다.
- 명령형, 함수형, 프로토타입 기반 객체지향 프로그래밍을 지원하는 멀티 패러다임 프로그래밍 언어
- 클래스 기반 객체지향 프로그래밍 언어보다 효율적이면서 강력하다.
3. 자바스크립트 실행 환경과 실행 방법
1) 자바스크립트 실행 환경
- 브라우저 : HTML, CSS, Javascript를 실행해 웹페이지를 브라우저 화면에 렌더링하는 것이 주된 목적
- DOM을 조작하는 DOM API를 기본적으로 제공
- DOM, BOM, Canvas, XMLHttpRequest, fetch, requestAnimation, Frame, SVG, Web Storage, Web Component, Web Worker와 같은 클라이언트 사이드 Web API 지원
- Node.js : 브라우저 외부에서 자바스크립트 실행 환경을 제공하는 것이 주된 목적
- 파일을 생성하고 수정할 수 있는 파일 시스템을 기본적으로 제공
- Node.js 고유의 API 지원
- 브라우저와 Node.js 기능의 교집합 = ECMASCript
2) 웹 브라우저
- 개발자 도구
- Elements : 로딩된 웹페이지의 DOM과 CSS를 편집해서 렌더링된 뷰를 확인해볼 수 있다.
- Console : 로딩된 웹페이지의 에러를 화인하거나 자바스크립트에 작성한 console.log메서드의 실행 결과를 확인할 수 있다.
- Sources : 로딩된 웹페이지의 자바스크립트 코드를 디버깅할 수 있다.
- Network : 로딩된 웹페이지에 관련된 네트워크 정보와 성능을 확인할 수 있다.
- Application : 웹 스토리지, 세션, 쿠키를 확인하고 관리할 수 있다.
3) Node.js
: 2009년, 크롬 V8자바스크립트 엔진으로 빌드된 자바스크립트 런타임 환경
- npm(Node Package Manager)
- Node.js에서 사용할 수 있는 모듈들을 패키지화해서 모아둔 저장소 역할 & 패키지 설치 및 관리를 위한 CLI 제공
4. 변수
- 변수 : 하나의 값을 저장하기 위해 확보한 메모리 공간 자체
- 그 메모리 공간을 식별하기 위해 붙인 이름
- 할당 : 변수에 값을 저장하는 것
- 참조 : 변수에 저장된 값을 읽어들이는 것
- 식별자 : 어떤 값을 구별해서 식별할 수 있는 고유한 이름
실행 콘텍스트
변수 이름을 비롯한 모든 식별자는 실행 콘텍스트에 등록된다. 실행 콘텍스트는 자바스크립트 엔진이 소스코드를 평가하고 실행하기 위해 필요한 환경을 제공하고 코드의 실행 결과를 실제로 관리하는 영역이다. 자바스크립트 엔진은 실행 콘텍스트를 통해 식별자와 스코프를 관리한다.
변수 이름과 변수 값은 실행 콘텍스트 내에 키/값 형식인 객체로 등록되어 관리된다.
호이스팅
변수 선언은 소스코드가 한 줄씩 순차적으로 실행되는 시점, 즉 런타임이 아니라 그 이전에 먼저 실행된다. 이렇게 변수 선언문이 코드의 선두로 끌어올려지는 것처럼 동작하는 자바스크립트 고유의 특징을 변수 호이스팅이라 한다. 변수 선언 뿐 아니라 var, let, const, function function*, class키워드를 사용해서 선언하는 모든 식별자는 호이스팅된다.
var a = 50;
위 코드를 컴퓨터는 var a;와 a=50으로 분리하여 계산한다. var a;는 선언 + 초기화(undefined로)이며 런타임 이전에 먼저 실행되고, a=50;은 할당 부분으로 런타임에 실행된다.
var a;
a = 50;
a = 80;
위 코드는 undefined > 50 > 80 세 개의 메모리 주소에 순차적으로 할당된다. 새로운 값을 할당할 때 같은 메모리 공간에 새롭게 값을 저장하는 것이 아니라, 새로운 메모리 공간을 확보하고 그 메모리 공간에 값을 저장한다. 불필요한 값들은 가비지 콜렉터에 의해 메모리에서 자동 해제된다.
자바스크립트는 메모리 관리 기능을 언어 차원에서 담당하고 개발자의 직접적인 메모리 제어를 허용하지 않는 매니지드 언어이다.
네이밍 컨벤션
- 카멜 케이스 : 변수나 함수
- 파스칼 케이스 : 생성자 함수, 클래스
5. 표현식과 문
- 값 : 식이 평가되어 생성된 결과
- 평가 : 식을 해석해서 값을 생성하거나 참조하는 것
10+20;10 + 20은 평가되어 숫자 30을 생성한다.
- 리터럴 : 사람이 이해할 수 있는 문자 또는 약속된 기호를 사용해 값을 생성하는 표기법
- 표현식 : 값으로 평가될 수 있는 문
var score = 100;
10;리터럴 표현식sum;식별자 표현식10+20;연산자 표현식
- 문 : 프로그램을 구성하는 기본 단위이자 최소 실행 단위
- 문의 집합으로 이뤄진 것이 프로그램이며, 문을 작성하고 순서에 맞게 나열한 것이 프로그래밍
- 문은 여러 토큰으로 구성된다.
- 토큰 : 문법적인 의미를 가지며, 문법적으로 더 이상 나눌 수 없는 코드의 기본 요소
var sum = 1 + 2;- 토큰 : var, sum, 1, + , 2, ;
- 문 :
var sum = 1 + 2;
- 표현식인 문은 값으로 평가될 수 있는 문이며, 표현식이 아닌 문은 값으로 평가될 수 없는 문이다.
var x;표현식이 아닌 문
x = 100;표현식인 문- 표현식인 문과 표현식이 아닌 문을 구별하는 가장 간단하고 명료한 방법은 변수에 할당해 보는 것이다.
6. 데이터 타입
원시 타입
- 숫자
- 모든 수를 실수로 처리
- 문자열
- boolean
- undefined : 개발자가 의도적으로 할당하기 위한 값이 아니라, 자바스크립트 엔진이 변수를 초기화할 때 사용하는 값
- null : 변수에 값이 없다는 것을 명시하고 싶을 때 사용
- Symbol
- BigInt
객체 타입
: 자바스크립트를 이루고 있는, 원시 타입을 제외한 모든 것
- 객체
- 함수
- 배열
데이터 타입의 필요성
- 값을 저장할 때 확보해야 하는 메모리 공간의 크기를 결정하기 위해
- 값을 참조할 때 한 번에 읽어들어야 할 메모리 공간의 크기를 결정하기 위해
- 메모리에서 읽어 들인 2진수를 어떻게 해석할지 결정하기 위해
동적 타이핑
- 정적 타입 언어 : 변수를 선언할 때 변수에 할당할 수 있는 값의 종류, 즉 데이터 타입을 사전에 선언
- C, C++, Java, Kotlin, Go, Haskell, Rust, Scala 등
- 동적 타입 언어 : 선언이 아닌 할당에 의해 타입이 결정
- 재할당에 의해 변수의 타입은 언제든지 동적으로 변할 수 있다. 이러한 특징을 동적 타이핑이라 하며, 자바스크립트를 동적 타입 언어라 한다.
- Javascript, Python, PHP, Ruby, Lisp, Perl
- 유연성은 높지만 신뢰성은 떨어진다.
- 변수 사용할 떄 주의 사항
- 변수의 무분별한 남발은 금물이며, 필요한 만큼 최소한으로 유지
- 변수의 스코프는 최대한 좁게 만들어 변수으 ㅣ부작용 억제
- 전역 변수 최대한 사용하지 않도록
- 변수보다는 상수를 사용해 값의 변경 억제
- 변수의 목적이나 의미를 파악할 수 있또록 네이밍
7. 연산자
산술 연산자
- 이항 산술 연산자
-
- / - / * /
// %
- / - / * /
-
- 단한 산술 연산자
- ++, —, +, -
- +는 피연산자를 숫자타입으로 변환하여 반환한다.
- ++, —, +, -
- -는 양수를 음수로, 음수를 양수로 반전환 값을 반환한다.
- 문자열 연결 연산자
- +
할당 연산자
- =, +=, -=, *=, /=, %=, **=
- 할당문은 값으로 평가되는 표현식인 문으로서 할당된 값으로 평가된다.
console.log(x=10);
- 따라서 할당문은 표현식인 문이다.
비교 연산자
- 동등/일치 비교 연산자
- ==, ===, ≠, ≠=
- **동등 비교연산자(==)**는 좌항과 우항의 피연산자를 비교할 때 먼저 암묵적 타입 변환을 통해 타입을 일치시킨 후 같은 값인지 비교한다.
- 이는 예측하기 어려운 결과를 만들어내며, 사용하지 않는 편이 좋다.
- **일치 비교 연산자(===)**는 좌항과 우항의 피연산자가 타입도 같고 값도 같은 경우에 한하여 true를 반환한다.
- NaN은 자신과 일치하지 않는 유일한 값이다. 따라서 숫자가 NaN인지 조사하려면 빌트인 함수
Number.isNaN을 사용한다. - 숫자 0도 주의하자. 자바스크립트에는 양의 0과 음의 0이 있는데, 이들을 비교하면 true를 반환한다.
Object.is는 +0과 -0은 다른 값으로, NaN과 NaN은 동일한 값으로 인식한다.
대소 관계 비교 연산자
-
, <, ≤, ≥
삼항 조건 연산자
if .. else문으로 대체하여 사용할 수 있지만, if .. else문은 표현식이 아닌 문이다. 따라서 이는 값처럼 사용할 수 없다.
const result = score > 60 ? 'pass' : 'fail'; // O
const result = if(score>60) {return 'pass'} // X
논리 연산자
- ||, &&, !
쉼표 연산자
왼쪽 피연산자부터 차례대로 피연산자를 평가하고 마지막 피연산자의 평가가 끝나면 마지막 피연산자의 평가 결과를 반환한다.
var x,y,z;
x=1, y=2, z=3;
그룹 연산자
( )로 피연산자를 감싸는 그룹 연산자는 자신의 피연산자인 표현식을 가장 먼저 평가한다.
typeof 연산자
- string, number, boolean, undefined, symbol, object, function 7가지 중 하나를 반환한다.
- 특이점은 null → object, 정규표현식 → object를 반환한다는 점이다.
- null이 object를 반환하는 것은 자바스크립트의 첫 번째 버그이며, 기존 코드에 영향을 줄 수 있기에 아직 수정되지 않았다.
- null타입인지 확인할 때는 typeof 연산자가 아닌 일치 연산자(===)를 사용해야 한다.
지수 연산자
- **
그 외 연산자
- ?.(옵셔널 체이닝 연산자), ??(Null 병합 연산자), delete, new, instanceof, in
부수효과가 있는 연산자
: 할당 연산자(=), 증가/감소 연산자(++,—), delete 연산자
8. 제어문
조건에 따라 코드 블록을 실행하거나 반복 실행을 할 때 사용한다.
1) 블록문
: 0개 이상의 문을 중괄호로 묶은 것
- 코드 블록, 블록이라고 부르기도 한다.
2) 조건문
: 주어진 조건식의 평가 결과에 따라 코드 블록의 실행을 결정한다.
- if .. else문 : 논리적 참, 거짓으로 실행할 코드 블록 결정
- switch문 : 다양한 상황에 따라 실행할 코드 블록 결정
- default를 제외한 앞선 case에서는 break문을 사용해야 한다.
3) 반복문
- for, while, do .. while
4) break문
-
레이블 문, 반복문(for, for .. in, for .. of, while, do .. while), switch문의 코드 블록 탈출
-
레이블 문
outer : for(){ for(){ if() break outer; } }위와 같이 레이블 문은 중첩된 For문 외부로 탈출할 때 유용하지만 그 밖의 경우에는 일반적으로 권장하지 않는다.
5) continue문
: 반복문으 코드 블록 실행을 현 지점에서 중단하고 반복문의 증감식으로 실행 흐름을 이동시킨다.
9. 타입 변환과 단축 평가
1. 명시적 타입 변환(=타입 캐스팅)
: 개발자가 의도적으로 값의 타입을 변환하는 것
- string 타입 변환
- String 생성자를 new 연산자 없이 호출
.toString()- 문자열 연결 연산자 사용
- number 타입 변환
- Number 생성자를 new 연산자 없이 호출
- parseIne, parseFloat 함수 사용
-
- 단항 산술 연산자
-
- 단항 산술 연산자
- boolean 타입 변환
- Boolean 생성자를 new 연산자 없이 호출
- ! 부정 논리 연산자 두 번 사용
2. 암묵적 타입 변환(=타입 강제 변환)
: 자바스크립트 엔진에 의해 암묵적으로 타입이 자동으로 변환되는 것
- string 타입 변환 :
xx + ‘’ - number 타입 변환 :
+xx - boolean 타입 변환 : 조건식의 평가 결과
- falshy : false, undefined, null, 0, -0, NaN, ‘’
3. 단축 평가
1) 논리 연산자
- 논리 곱 연산자(&&), 논리 합 연산자(||)
- 논리 연산의 결과를 결정하는 피연산자 반환
- ‘Cat’ || ‘Dog’ // ‘Cat’
- false || ‘Dog’ // ‘Dog’
- ‘Cat’ && ‘Dog’ // ‘Dog’
- flase && ‘Dog’ // flase
- if문 대체
- && : if문 대체
- || : if not문 대체
- const message = done || ‘미완료’
- done이 false라면 뒤의 ‘미완료’가 message에 할당
- const message = done || ‘미완료’
- 객체를 가리키기를 기대하는 변수가 Null 또는 undefined가 아닌지 확인하고 프로퍼티를 참조할 때
- const value = elum && elum.value;
- elem이 truthy값이면 elem.vluae로 평가되고, falshy값이면 elem으로 평가된다.
- const value = elum && elum.value;
- 기본값을 설정할 때
- const a = b || ‘c’
2) 옵셔널 체이닝 연산자(?.)
좌항의 피연산자가 null 또는 undefined인 경우 undefined를 반환하고, 그렇지 않으면 우항의 프로퍼티 참조를 이어간다.
- 객체를 가리키기를 기대하는 변수가 Null 또는 Undefined가 아닌지 화인하고 프로퍼티를 참조할 때 유용하다.
- 좌항 피연산자가 falshy값이여도, null이나 Undefined가 아니라면 우항의 프로퍼티 참조를 이어간다.
- 이에 반해 논리 연산자 &&는 좌항의 피연산자가 falshy라면 해당 피연산자를 그대로 반환한다.
3) null 병합 연산자(??)
좌항의 피연산자가 null 또는 undefined인 경우 우항의 피연산자를 반환하고, 그렇지 않으면 좌항의 피연산자를 반환한다.
- 변수에 기본값을 설정할 때 유용하다.
const a = b ?? ‘default string’;
-
이에 반해 논리 연산자 || 좌항의 피연산자가 falshy라면 우항의 피연산자를 반환한다. 이는 예기치 않은 동작이 발생할 수 있다.
10. 객체 리터럴
자바스크립트는 개체 기반의 프로그래밍 언어이며, 자바스크립트를 구성하는 거으 ㅣ모든 것이 객체이다. 원시값을 제외한 나머지 값(함수, 배열, 정규표현식 등)은 모두 객체다.
- 원시타입은 단 하나의 값을 나타내지만 객체 타입은 다양한 타입의 값을 하나의 단위로 구성한 복합적인 자료구조이다.
- 원시 값은 변경 불가능한 값이지만, 객체는 변경 가능한 값이다.
- 객체는 0개 이상의 프로퍼티로 구성된 집합이며, 프로퍼티는 키와 값으로 구성된다.
- 값이 함수일 때 이는 일반 함수와 구분하기 위해 메서드라 부른다.
- 프로퍼티 : 객체으 ㅣ상태를 나타내는 값
- 메서드 : 프로퍼티를 참조하고 동작할 수 있는 함수
객체 생성 방법
- 객체 리터럴
- Object생성자 함수
- 생성자 함수
- Object.create 메서드
- 클래스
프로퍼티
객체는 프로퍼티의 집합이며, 프로퍼티는 키와 값으로 구성된다.
- 프로퍼티 키 : 빈 문자열을 포함한 모든 문자열 또는 심벌 값
- 식별자 네이밍 규칙을 준수하지 않으면 ‘’ 따옴표를 붙여야하며, 준수하는 것을 권장한다.
- 프로퍼티 값 : 자바스크립트에서 사용할 수 있는 모든 값
- 프로퍼티 접근
- 마침표 표기법
- person.name
- 마침표 표기법
- 대괄호 표기법
- person[’name’]
- 프로퍼티 키가 네이밍 규칙을 준수하지 않는 경우라면 대괄호 표기법을 사용해야한다.
- 프로퍼티 값 갱신 : 이미 존재하는 프로퍼티 값을 할당하면 프로퍼티 값이 갱신된다.
- 프로퍼티 동적 생성 : 존재하지 않는 값을 할당하면 동적으로 생성되어 프로퍼티 값이 할당된다.
- 프로퍼티 삭제
delete person.name
ES6에서 추가된 객체 리터럴의 확장 기능
- 프로퍼티 축약 표현 : 변수 이름과 프로퍼티 키가 동일한 이름일 때 프로퍼티 키 생략
- 계산된 프로퍼티 이름 : 문자열 또는 문자열로 타입 변환할 수 있는 값으로 평가되는 표현식을 사용해 프로퍼티 키를 동적으로 생성
obj[prefix + ‘-’ + ++i ] = i;
- 메서드 축약 표현
- `const obj = { sayHi(){ console.log(’a’); }
}`
11. 원시 값과 객체의 비교
- 원시값(원시타입의 값)은 변경 불가능하다. 객체(객체타입의 값)는 변경 가능하다.
- 원시값을 변수에 할당하면 변수에는 실제 값이 저장된다. 객체를 변수에 할당하면 벼수에는 참조값이 저장된다.
- 원시값을 갖는 변수를 다른 변수에 할당하면 원시값이 복사되어 전달된다(값에 의한 전달). 객체를 가리키는 변수를 변수를 다른 변수에 할당하면 원본의 참조 값이 복사되어 전달된다.(참조에 의한 전달)
1. 원시값
“원시 값은 변경 불가능하다”는 것은 원시값 자체를 변경 불가능하다는 것이지, 변수 값을 변경할 수 없다는 것은 아니다. 변수는 언제든지 재할당을 통해 변수 값을 변경할 수 있다. 그렇기에 변수라 부른다. 변수에는 다른 메모리 공간을 차지하는 원시값이 재할당되는 것이다.
문자열과 불변성
ECMAScript사양에 문자열 타입(2byte), 숫자 타입(8byte)이외의 원시 타입의 크기를 명화히 규정하고 있지 않아 브라우저 제조사의 구현에 따라 원시 타입의 크기는 다를 수 있다.
문자열은 원시타입이기에 문자열 또한 변경 불가능하다.
문자열은 유사 배열 객체이면서 이터러블이므로 배열과 유사하게 각 문자에 접근할 수 있다.
- 유사 배열 객체 : 배열처럼 인덱스로 프로퍼티에 접근할 수 있고 length프로퍼티를 가진 객체
2. 객체
자바스크립트 엔진은 해시 테이블과 유사하지만, 높은 성능을 위해 일반적인 해시 테이블보다 더 나은 방법으로 객체를 구현한다.
객체는 변경 가능한 값이다. 객체를 할당한 변수가 기억하는 메모리 주소를 통해 메모리 공간에 접근하면 참조값에 접근할 수 있다. 참조값은 생성된 객체가 저장된 메모리 공간의 주소, 그 자체다.
12. 함수
: 입력을 받아 출력을 내보내는 일련의 과정
- 일련의 과정을 문으로 표현하고, 코드 블록으로 감싸서 하나의 실행 단위로 정의한 것
- 용어
- 매개변수 : 함수 내부로 입력을 전달받는 변수
- 인수 : 입력(실제 입력)
- 반환값 : 출력
함수를 사용하는 이유
- 코드 재사용
- 유지보수의 편의성
- 실수를 줄여 코드의 신뢰성
- 코드의 가독성 향상
1. 함수 선언문
함수 선언문은 함수 리터럴과 다르게 함수 이름을 생략할 수 없다.
-
함수 리터럴
const a = function add(x,y){ return x+y; }- 변수에 함수 리터럴을 할당
함수 선언문은 표현식이 아닌 문이다.
- 콘솔에서 함수 선언문을 실행하면 완료값 undefined가 출력된다. 만약 표현식인 문이라면 undefined 대신 표현식이 평가되어 생성된 함수가 출력되어야 한다.
함수 선언문과 함수 리터럴은 비슷하게 생겼지만 다른 방식으로 동작하며, 중의적인 코드이다. 코드의 문맥에 따라 해석이 달라질 수 있다.
자바스크립트 엔진은 생성된 함수를 호출하기 위해 함수 이름과 동일한 이름의 식별자를 암묵적으로 생성하고, 거기에 함수 객체를 할당한다.
const add = function add (x,y){
return x+y;
}
위 코드처럼, add함수를 함수 선언문으로 선언하면, add식별자에 할당이 된다.
하지만, 함수 표현식과 정확히 동일하게 동작하는 것은 아니다.
2. 함수 표현식
자바스크립트에서 함수는 일급 객체이므로 함수를 값처럼 자유롭게 사용할 수 있다.
호이스팅
모든 선언문이 그렇든 함수 선언문도 런타임 이전에 자바스크립트 엔진에 의해 먼저 실행된다 : 호이스팅
이 때, 함수 표현식으로 함수를 정의하면 함수 호이스팅이 발생하는 것이 아니라 변수 호이스팅이 발생한다. 함수 표현식 이전에 함수를 참조하면 undefined(var 선언의 경우)로 평가된다. 따라서 이 때 함수를 호출하면 undefined를 호출하는 것과 마찬가지이므로 타입 에러가 발생한다.
JSON 창안한 더글라스 크락포는 함수 선언문 대신 함수 표현식 사용을 권장한다.
Function 생성자 함수
클로저 생성하지 않고, 함수 선언문 혹은 표현식으로 생성한 함수와 다르게 동작한다.
즉시 실행 함수
(fucntion (){
const a = 3;
const b = 8;
return a + b;
})
즉시 실행함수는 반드시 그룹 연산자 ( ) 로 감싸야 한다.
값의 전달
const res = (function (a,b){
return a+b;
})(3,5);
console.log(res); // 15
콜백 함수
: 함수의 매개변수를 통해 다른 함수의 내부로 전달되는 함수
고차 함수
: 매개변수를 통해 함수의 외부에서 콜백 함수를 전달받은 함수
순수 함수
: 부수효과가 없는 함수
- 순수 함수는 일반적으로 최소 하나 이상의 인수를 전달받는다. 인수를 전달받지 않는 상수는 상수와 다름 없다.
13. 스코프
: 식별자가 유효한 범위
모든 식별자(변수 이름, 함수 이름, 클래스 이름 등)는 자신이 선언된 위치에 의해 다른 코드가 식별자 자신을 참조할 수 있는 유효 범위가 결정된다.
- 식별자 결정 : 이름이 같은 두 개의 변수 중 어떤 변수를 참조해야할 지 결정하는 것. 스코프은 자바스크립트 엔진이 식별자를 검색할 때 사용하는 규칙이라 할 수 있다.
스코프 체인
: 스코프가 계층적으로 연결된 것
- Javascript 엔진은 변수를 참조할 떄 스코프 체인을 통해 변수를 참조하는 코드의 스코프에서 시작하여 상위 스코프 방향으로 이동하여 선언된 변수를 검색한다.
- 스코프 체인은 물리적인 실체로 존재한다. 자바스크립트 엔진은 코드를 실행하기에 앞서 렉시컬 환경을 실제로 생성한다.
- 변수 선언이 실행되면 변수 식별자가 렉시컬 환경에 등록되고, 변수 할당이 일어나면 이 자료구조의 변수 식별자에 해당하는 값을 변경한다.
- 스코프는 함수에도 해당이 되기 때문에, ‘변수를 검색할 때 사용하는 규칙'보다는 ‘식별자를 검색하는 규칙’에 가깝다.
함수 레벨 스코프
var 키워드는 함수 레벨 스코프, let, const키워드는 블록 레벨 스코프를 지원한다.
렉시컬 스코프
- 동적 스코프 : 함수를 어디서 호출했는지에 따라 함수의 상위 스코프를 결정한다.
- 정적 스코프(= 렉시컬 스코프) : 함수를 어디서 정의했는지에 따라 함수의 상위 스코프를 결정한다.
- JS를 비롯한 대부분의 프로그래밍 언어는 이를 따른다.
- 함수의 상위 스코프는 어디서 호출되었는지에 따라 무관하고, 자신이 정의된 스코프이다.
14. 전역 변수의 문제점
전역 변수의 생명 주기는 애플리케이션의 생명 주기와 같다. 하지만, 함수 냉부에서 선언된 지역변수는 함수가 호출되면 생성되고 함수가 종료되면 소멸한다.
- 변수 선언은 코드가 한 줄씩 순차적으로 실행되는 시점인 런타임에 실행되는 것이 아니라, 런타임 이전 단계에서 자바스크립트 엔진에 의해 먼저 실행된다.
- 단, 전역 변수에 한정된 것이다. 함수 내부에서 선언한 변수는 함수가 호출된 직후에 위와같은 방식이 동작한다.
- 즉, 호이스팅은 스코프를 단위로 동작한다.
전역 객체
: 클라이언트 사이드 환경(브라우저)에서는 window, 서버 사이드 환경(Node.js)에서는 global 객체를 의미한다.
- 표준 빌트인 객체(Object, ARray, String ..)와 환경에 따른 호스트 객체(Web Api 또는 Node.js의 호스트 API), 그리고 var키워드로 선언한 전역 변수와 전역 함수의 프로퍼티로 갖는다.
전역 변수의 문제점
- 암묵적 결합 : 모든 코드가 전역 변수를 참조하고 변경할 수 있다.
- 긴 생명 주기
- 스코프 체인 상에서 종점에 존재 → 검색 속도가 느리다.
- 네임스페이스 오염
전역 변수의 사용 억제하는 방법
- 즉시 실행 함수
- 네임스페이스 객체
- 네임스페이스 역할을 담당할 객체를 생성하고 전역 변수처럼 사용하고 싶은 변수를 프로퍼티로 추가하는 방법
- 모듈 패턴 : 클로저 활용한 방식
- ES6 : 파일 자체의 독자적인 모듈 스코프 제공
- 아직까지는 ES6모듈 기능보다는 Webpack 등의 모듈 번들로 사용하는 것이 일반적이다.
15. let, const 키워드와 블록 레벨 스코프
var 키워드로 선언한 변수
-
변수 중복 선언 허용
var a = 1; console.log(a); // 1 var a = 5; console.log(a); // 5 var a; console.log(a); // 5- 초기화문이 있는 변수 선언문은 자바스크립트 엔진에 의해 var키워드가 없는 것처럼 동작한다.
- 초기화문이 없는 변수 선언문은 무시한다.
-
함수 레벨 스코프
var a = 1; console.log(a); // 1 function b() { console.log(a); // error var a; } console.log(a); // 1 b();- 함수의 코드 블록만을 지역 스코프로 인정한다.
- 위와 같은 경우, b함수를 실행했을 때 b함수의 렉시컬 스코프가 생성이 되며 a식별자를 렉시컬 스코프에 등록하게 된다. 이 때 변수의 선언과 초기화가 일어나기 때문에 undefined를 출력하게 된다.
let 키워드로 선언한 변수
-
변수 중복 선언 금지
-
블록 레벨 스코프
let a = 1; console.log(a); // 1 function b() { console.log(a); // error let a; } b();- 모든 코드 블록(함수, if문, for문, while문, try/catch 문 등)을 지역스코프로 인정하는 블록 레벨 스코프를 따른다.
-
변수 호이스팅
- var키워드로 선언한 변수는 런타임 이전에 암묵적으로 선언 단계와 초기화 단계가 한 번에 진행된다.
- 선언 단계 : 스코프(실행 컨텍스트의 렉시컬 환경)에 변수 식별자를 등록해 자바스크립트 엔진에 변수의 존재를 알린다.
- var키워드로 선언한 변수는 런타임 이전에 암묵적으로 선언 단계와 초기화 단계가 한 번에 진행된다.
- 초기화 단계 : undefined로 변수를 초기화한다.
- let키워드로 선언한 변수는 선언 단계와 초기화 단계가 분리되어 진행된다.
- 일시적 사각지대(TDZ) : 스코프의 시작 지점부터 초기화 시작 지점까지 변수를 참조할 수 없는 구간
- 자바스크립트는 모든 선언(var, let, const, function, function*, class 등)을 호이스팅한다.
- 단, ES6에서 도입된 let, const, class를 사용한 선언문은 호이스팅이 발생하지 않는 것처럼 동작한다.
전역 객체와 let
let키워드로 선언한 전역 변수는 전역 객체의 프로퍼티가 아니다. var키워드로 선언한 전역 변수는 전역 객체의 프로퍼티가 된다.
var a = 1;
window.a; // 1
let b = 2;
window.b; // undefined
const키워드로 선언한 변수
- 반드시 선언과 동시에 초기화해야 한다.
- 재할당 금지
- 상수를 표현하는 데 사용
- const키워드로 선언된 변수에 객체를 할당할 경우 값을 변경할 수 있다.
- const키워드는 재할당을 금지할 뿐 ‘불변’을 의미하지는 않는다.
- 새로운 값을 재할당하는 것은 불가능하지만 프로퍼티 동적 생성, 삭제, 변경을 통해 객체를 변경하는 것은 가능하다.
- 객체가 변경되더라도 변수에 할당된 참조 값은 변경되지 않는다.
변수를 선언할 때는 일단 const를 사용하자. 반드시 재할당이 필요하다면 그 때 const키워드를 let키워드로 변경해도 결코 늦지 않다.
18. 함수와 일급 객체
일급 객체의 조건
- 무명의 리터럴로 생성할 수 있다. 즉, 런타임에 생성이 가능하다.
- 변수나 자료구조(객체, 배열 등)에 저장할 수 있다.
- 함수의 매개변수에 전달할 수 있다.
- 함수의 반환값으로 사용할 수 있다.
자바스크립트에서 함수는 위의 조건을 모두 만족하므로 일급 객체다.
함수 객체의 프로퍼티
함수도 객체이기에 프로퍼티를 가질 수 있다.

- arguments
-
함수 호출 시 전달된 인수들의 정보를 담고 있는 순회 가능한 유사 배열 객체
function multiply(x,y){ const iterator = arguments[Symbol.iterator](); console.log(iterator.next()); // {value:1, done:false} console.log(iterator.next()); // {value:2, done:false}; console.log(iterator.next()); // {value:3, done:true}; } multiply(1,2);유사 배열 객체는 배열이 아니므로 배열 메서드를 사용할 경우 에러가 발생한다. Function.prototype.call, Function.prototype.apply를 사용해 간접 호출해야한다.
function multiply(){ const array = Array.prototype.slice.call(arguments); return array.reduce((a,b)=>a+b,0); } multiply(1,4,5); // 10
-
자바스크립트는 매개변수와 인수의 개수가 일치하는지 확인하지 않는다.
- 가변 인자 함수를 구현할 때 유용하다. 하지만 ES6 spread연산자의 등장 이후 중요성이 이전같지 않다.
- length : 함수를 정의할 때 선언한 매개변수의 개수
- caller : 함수 자신을 호출한 함수
- ECMAScript 사양에 포함되지 않은 비표준 프로퍼티니 사용하지 말고 참고로만 알아두기
- name : 함수 이름
- prototype : 생성자 함수로 호출할 수 있는 함수 객체, 즉 constructor만이 소유하는 프로퍼티
19. 프로토타입
자바스크립트는 명령형, 함수형, 프로토타입 기반, 객체지향 프로그래밍을 지원하는 멀티 패러다임 프로그래밍 언어다.
ES6에서 추가되 클래스는 또한 함수이며, 기존 프로토타입 기반 패턴의 문법적 설탕이다. 하지만 단순한 문법적 설탕으로 보기보다는 새로운 객체 생성 매커니즘으로 보는 것이 더 합당하다.
객체 지향 프로그래밍
: 프로그램을 명령어, 함수의 목록으로 보는 전통적인 명령형 프로그래밍의 절차지향적 관점에서 벗어나 여러 개의 독립적 단위, 즉 객체의 집합으로 프로그램을 표현하는 프로그래밍 패러다임
- 객체의 상태를 나타내는 데이터와 상태 데이터를 조작할 수 있는 동작을 하나의 논리적인 단위로 묶어 생각한다.
- 객체는 상태 데이터와 동작을 하나의 논리적인 단위로 묶은 복합적인 자료구조라 할 수 있다.
상속과 프로토타입
- 상속 : 객체 지향 프로그래밍의 핵심 개념으로, 어떤 객체의 프로퍼티 또는 메서드를 다른 객체가 상속받아 그대로 사용할 수 있는 것
function Circle(radius) {
this.radius = radius;
}
Circle.prototype.getArea = function () {
return Math.PI * this.radius ** 2;
};
const circle1 = new Circle(2); // 12.53...
console.log(circle1.getArea());
상속은 코드의 재사용의 관점에서 매우 유용하다.
**proto**접근자 프로퍼티
모든 객체는 __proto__접근자 프로퍼티를 통해 자신의 프로토타입, 즉 [[prototype]]내부 슬롯에 접근할 수 있다.
-
proto는 접근자 프로퍼티다.
- 자체적으로 값을 갖지 않고, 다른 프로퍼티의 값을 읽거나 저장할 때 사용하는 접근자함수로 구성된 프로퍼티다.
-
proto접근자 프로퍼티는 상속을 통해 사용된다.
-
proto접근자 프로퍼티는 Object.prototype의 프로퍼티다.
-
-
proto접근자 프로퍼티를 코드 내에서 직접 사용하는 것은 권장하지 않는다.
prototype 프로퍼티
: 생성자 함수가 생성할 인스턴스의 프로토타입
-
함수 객체는 prototype프로퍼티를 소유하고, 일반 객체는 소유하지 않는다.
prototype프로퍼티는 생성자 함수가 생성할 객체(인스턴스)의 프로토타입을 가리킨다.따라서, 생성자 함수로서 호출할 수 없는 함수, 즉 non-constructor인 화살표 함수와 ES6 메서드 축약 표현으로 정의한 메서드는 prototype프로퍼티를 소유하지 않는다.
-
모든 객체가 가지고 있는 **proto**(Object.prototype으로부터 상속받은)접근자 프로퍼티와 함수 객체만이 가지고 있는 prototype프로퍼티는 결국 동일한 프로토타입을 가리킨다.
constructor 프로퍼티
: prototype 프로퍼티로 자신을 참조하고 있는 생성자 함수를 가리킨다.
person2객체는 프로토타입인 Person.prototype의 constructor프로퍼티를 상속받아 사용할 수 있다.
Strict Mode
: 자바스크립트 언어의 문법을 좀 더 엄격히 적용하여 오류를 발생시킬 가능성이 높거나 JS엔진의 최적화 작업에 문제를 일으킬 수 있는 코드에 대해 명시적인 에러를 발생시킨다.
-
ES5에서 추가되었다.
-
암묵적 전역
function foo(){ x=10; } foo(); console.log(x); // 10foo함수 내부에서 x변수의 선언을 검색한다 > foo함수의 스코프에는 x변수의 선언이 없기 때문에 상위 스코프인 전역 스코프에서 검색한다 > x 변수 선언이 없다.
하지만, JS엔진은 암묵적으로 전역 객체에 x프로퍼티를 동적 생성한다. 이 때 전역 객체의 x프로퍼티는 마치 전역 변수처럼 사용할 수 있다.
암묵적 전역은 오류를 발생시키는 원인이 될 가능성이 크다. 따라서 반드시 var,let,const 키워드로 선언 후 사용해야 한다.
-
ESLint같은 린트 도구를 사용해더 strict mode와 유사한 효과를 얻을 수 있다.
- 린트 도구 : 정적 분석 기능을 통해 소스코드를 실행하기 전 소스코드를 스캔하여 문법적 오류 뿐 아니라 잠재적 오류까지 찾아내 오류의 원인을 리포팅해준다.
- strict mode가 제한하는 오류까지 린트에서 강제할 수 있다.
선언 방법
- 전역의 선두 혹은 함수 몸체의 선두에
‘use strict’;를 추가한다.- 전역에 감싸는 건 바람직 하지 않다. 필요하다면 즉시 실행 함수로 감싸, 선두에 strict mode를 적용하자.
strict mode가 발생시키는 에러
- 암묵적 전역 : 선언하지 않는 변수를 참조할 때
- 변수,함수, 매개변수의 삭제(delete)
- 매개변수 이름의 중복
- with문의 사용
strict mode적용에 의한 변화
- 일반 함수의 this
- 생성자 함수가 아닌 일반 함수 내부에서 this를 사용할 필요가 없다(전역을 가리킨다). 따라서 에러를 발생시킨다.
function A(){
console.log(this);
}
A(); // 일반 함수, 전역 객체(window/global)
new A(); // 생성자 함수
- argumenets 객체에 인자값 변경으로 인한 변경이 적용되지 않는다.
빌트인 객체
자바스크립트의 객체는 3개의 객체로 분류할 수 있다.
- 표준 빌트인 객체 : ECMAScript사양에 정의된 객체
- 애플리케이션 전역의 공통 기능을 제공한다.
- JS 실행 환경에 관계없이 언제나 사용할 수 있다.
- 호스트 객체 : JS 실행 환경에서 추가로 제공하는 객체
- 브라우저 환경(window) : DOM, BOM, Canvas, XMLHttpRequest, fetch 등 클라이언트 사이드 Web API
- Node.js 환경(global) : fs, path 등
- 사용자 정의 객체 : 사용자가 직접 정의한 객체
표준 빌트인 객체
- Object, String, Number, Booolean, Symbol, Date .. 등 40 여개 제공
- Math, Refelect, JSON를 제외한 표준 빌트인 객체는 모두 인스턴스를 생성할 수 있는 생성자 함수 객체
- 생성자 함수 객체인 표준 빌트인 객체 : 프로토타입 메서드와 정적 메서드 제공
- e.g. String, Number, Boolean, Array ..
- 생성자 함수 객체인 표준 빌트인 객체 : 프로토타입 메서드와 정적 메서드 제공
- 생성자 함수 객체가 아닌 표준 빌트인 객체 : 정적 메서드만 제공
원시값과 래퍼 객체
원시값에서 메서드를 사용할 수 있는 이유?
: 원시값에 객체처럼 접근하면 래퍼 객체가 생성이 되고, 해당 객체에서 메서드를 사용하기 때문.
- String, Number, Boolean, Symbol : 프로토타입 메서드 또는 프로퍼티를 참조할 수 있다.
- null, undefined : 래퍼 객체를 생성하지 않는다.
전역 객체
: 코드가 실행되기 이전 단계에 JS 엔진에 의해 어떤 객체보다도 먼저 생성되는 특수한 객체이며, 어떤 객체에도 속하지 않는 최상위 객체이다.
-
브라우저 환경 : window, Node.js환경에서는 global이 전역 객체를 가리킨다.
- globalThis는 ECMAScript 표준사양으로, 모든 환경에서 사용할 수 있다.
-
전역 객체의 프로퍼티를 참조할 때 window/global을 생략할 수 있다.
-
var키워드로 선언한 변수, 선언하지 않은 변수에 값을 할당한 암묵적 전역, 전역 함수는 전역 객체의 프로퍼티가 된다.
-
브라우저 환경에서 모든 JS코드는 script로 구분이 되어 있어도, 하나의 window를 공유한다.
- 빌트인 전역 프로퍼티
- Infinity, NaN, undefined
- 빌트인 전역 함수
- eval : 표현식은 런타임에 평가하여 값을 생성하고, 문이라면 런타임에 실행한다.
- JS엔진에 의해 최적화가 수행되지 않으므로 일반적인 코드 실행에 비해 느리므로 사용을 금지해야 한다.
- eval : 표현식은 런타임에 평가하여 값을 생성하고, 문이라면 런타임에 실행한다.
- isFinite, isNaN, parseFloat, parseInt