느슨한 타입(loosely typed)의 동적(dynamic) 언어
let foo = 42 // foo가 숫자
foo = 'bar' // foo가 이제 문자열
foo = true // foo가 이제 불리언
JavaScript의 타입
원시값 : 객체를 제외한 모든 타입은 불변 값(변경할 수 없는 값)을 정의합니다. 예를 들어 (C 언어와는 달리) 문자열은 불변합니다. 이런 일련의 타입을 "원시 값"이라고 합니다.
Boolean 타입
Boolean 타입은 논리 요소를 나타내며 true와 false 두 가지의 값을 가질 수 있습니다.
Null 타입
Null 타입은 null 하나의 값만 가질 수 있습니다.
Undefined 타입
값을 할당하지 않은 변수는 undefined 값을 가집니다.
Number 타입
ECMAScript는 Number와 BigInt 두 가지의 내장 숫자 타입을 가지고 있습니다. 부동소수점 숫자 외에도 +Infinity, -Infinity, NaN("Not a Number") 세 개의 상징적인 값을 가집니다.
BigInt 타입
BigInt 타입은 임의 정밀도로 정수를 나타낼 수 있는 JavaScript 숫자 원시 값입니다. BigInt를 Number의 안전 한계를 넘어서는 큰 정수도 안전하게 저장하고 연산할 수 있습니다.
BigInt는 정수 끝에 n을 추가하거나 생성자를 호출해 생성할 수 있습니다.
String 타입
JavaScript의 String 타입은 텍스트 데이터를 나타낼 때 사용합니다. String은 16비트 부호 없는 정수 값 "요소"로 구성된 집합으로, 각각의 요소가 String의 한 자리를 차지합니다. 첫 번째 요소는 인덱스 0에, 그 다음 요소는 인덱스 1, 그 다음은 2, ...입니다. String의 길이는 그 안의 요소 수와 같습니다.
C 언어와 같은 일부 프로그래밍 언어와 달리 JavaScript 문자열은 불변합니다. 즉 문자열을 생성한 후 바꾸는 것은 불가능합니다.
그러나 원본 문자열을 사용해 새로운 문자열을 생성하는 것은 가능합니다.
Symbol 타입
Symbol은 고유하고 변경 불가능한 원시 값이며 객체의 속성(아래를 참고하세요) 키로 사용할 수 있습니다. 어떤 프로그래밍 언어들에선 "아톰"이라고 부르기도 합니다.
JavaScript 형변환(Type Casting)
자바스크립트는 타입이 매우 유연한 언어이다. 때문에 자바스크립트 엔진이 필요에 따라 암시적변환을 혹은 개발자의 의도에 따라 명시적변환을 실행한다.
let num = 10
console.log(num, typeof num) // 10 "number"
num = num.toString()
console.log(num, typeof num) // 10 "string"
num = parseInt(num)
console.log(num, typeof num) // 10 "number"
let variable = 100
console.log(variable, typeof variable) // 100 "number"
variable = Object(variable)
console.log(variable, typeof variable) // Number {100} "object"
variable = String(variable)
console.log(variable, typeof variable) // 100 "string"
variable = Boolean(variable)
console.log(variable, typeof variable) // true "boolean"
== , ===의 차이점
==
a와 b의 값이 같은지를 비교해서, 같으면 true, 다르면 false라고 한다.(값만 같으면 true이다.)
'==='값과 값의 종류(Data Type)가 모두 같은지를 비교해서, 같으면 true, 다르면 false라고 한다.
변수를 비교하거나 어떤 비교를 위해 항상 '===' 연산자를 사용 할 것을 권장한다.
가능한 '==' 연산자를 사용하지 않도록 하고, 대신 직접 자료형을 변환하여(casting) 보다 코드 가독성을 높이도록 한다.
undefined와 null의 미세한 차이
기본형과 참조형의 종류 및 차이점
불변 객체를 만드는 방법
const
자바스크립트 키워드 중 하나인 const이다. ES6문법부터 let과 const를 지원한다.
const 키워드는 변수를 상수로 선언할 수 있다, 일반적으로 상수로 선언된 변수는 값을 바꾸지 못하는 것으로 알려져 있다.
Object.freeze()
자바스크립트에서 기본적으로 제공하는 메소드인 Object.freeze() 메소드이다. 공식 문서에서는 "객체를 동결하기 위한 메소드" 라고 적혀있다.
const와 Object.freeze()를 조합하여 만들 수 있다. (const의 재할당불가 + Object.freeze()의 객체속성 변경불가)
먼저 const키워드로 바인딩 된 변수를 상수화 시킨 다음, Object.freeze()로 해당 변수를 동결 객체를 만들면
객체의 재할당과 객체의 속성 둘 다 변경불가능한 불변 객체가 된다.
const test = {
'name' : 'jung'
};
Object.freeze(test);
얕은 복사와 깊은 복사
얕은 복사
객체를 복사할 때 위의 예제처럼 원래값과 복사된 값이 같은 참조를 가리키고있는 것을 말한다. 객체안에 객체가 있을 경우 한개의 객체라도 원본 객체를 참조하고 있다면 이를 얕은 복사라고 한다.
-1. Object.assign()
-2. 전개연산자
깊은 복사
깊은 복사된 객체는 객체안에 객체가 있을 경우에도 원본과의 참조가 완전히 끊어진 객체를 말한다.
스코프, 호이스팅, TDZ
호이스팅
함수의 코드를 실행하기 전에 함수 선언에 대한 메모리부터 할당한다. 덕분에 스크립트내에서 함수 선언의 위치는 중요하지 않다. 스크립트내에서 함수 호출을 함수 선언보다 먼저 해도 문제가 없다. 또 호이스팅은 스코프 단위로 일어난다..
자바스크립트는 ES6에서 도입된 let, const를 포함하여 모든 선언(var, let, const, function, function*, class)을 호이스팅합니다. 호이스팅(Hoisting)이란, var 선언문이나 function 선언문 등을 해당 스코프의 선두로 옮긴 것처럼 동작하는 특성을 말합니다.
TDZ
스코프 시작 ~ 초기화 시작 사이의 구간을 의미합니다. 다른 말로 변수가 선언되고 변수의 초기화가 이루어지기 전까지의 구간이라고 말할 수 있겠습니다.
함수 선언문과 함수 표현식에서 호이스팅 방식의 차이
주요 차이점은, 호이스팅에서 차이가 발생합니다.
함수 선언식은 함수 전체를 호이스팅 합니다. 정의된 범위의 맨 위로 호이스팅되서 함수 선언 전에 함수를 사용할 수 있다는 것입니다.
함수 표현식은 별도의 변수에 할당하게 되는데, 변수는 선언부와 할당부를 나누어 호이스팅 하게 됩니다. 선언부만 호이스팅하게 됩니다.
호이스팅은 var 변수 선언, 함수선언식에서만 일어난다. let/const에서는 호이스팅이 발생하지 않는다.
var minus = function (a,b) { // 함수 표현식
return a - b;
}
sum(50, 50); // 100
minus(100, 50) // 50
function sum(a, b) { // 함수 선언식
return a + b;
};
실행 컨텍스트와 콜 스택
자바스크립트 엔진은 처음 코드를 실행할 떄 단 한번 Global Execution Context를 생성하며 함수를 호출할 때 마다 함수를 위한 Execution context를 생성합니다.
콜 스택(Call stack)
스코프 체인, 변수 은닉화
스코프 체인 : 식별자에 대한 유효 범위를 나타낸다.떤 경계 A의 외부에서 선언한 변수는 A의 외부뿐 아니라 A의 내부에서도 접근이 가능하지만, A의 내부에서 선언한 변수는 오직 A의 내부에서만 접근할 수 있다. 이러한 식별자의 유효범의를 안에서부터 바깥으로 차례로 검색해나가는 것을 스코프 체인이라고 부른다.
변수은닉화 : 외부 객체로부터 '속성 값(데이터, 멤버 변수값)'을 감추는 특성
접근제어자 private로 감춘다. (private - class내에서만 접근가능)
private를 사용하는 이유 ?
외부로부터 데이터를 보호(캡슐화)하기 위해서
인스턴스 변수는 private로 하여 외부에서 접근하지 못하도록 하고, 메서드는 public으로 하여 직접 접근은 막고 메서드를 통한 간접 접근 허용
외부에는 불필요한, 내부적으로만 사용되는 , 부분을 감추기 위해서
콘솔에 찍힐 b 값을 예상해보고, 어디에서 선언된 “b”가 몇번째 라인에서 호출한 console.log에 찍혔는지, 왜 그런지 설명해보세요.
주석을 풀어보고 오류가 난다면 왜 오류가 나는 지 설명하고 오류를 수정해보세요.
let b = 1;
function hi () {
const a = 1;
let b = 100;
b++;
console.log(a,b);
}
//console.log(a);
console.log(b);
hi();
console.log(b);
풀이
let b = 1;
function hi () {
const a = 1;
let b = 100;
b++;
console.log(a,b);
}
//console.log(a);
console.log(b); // 첫 줄 b =1
hi();
console.log(b); // 첫 줄 b =1
let b = 1;
function hi () {
const a = 1;
let b = 100;
b++;
console.log(a,b);
}
console.log(a);
console.log(b);
hi();
console.log(b);
// a가 지역스코프로 선언되어 바깥의 범위에서는 console 불가
let b = 1;
const a = 1;
function hi () {
let b = 100;
b++;
console.log(a,b);
}
console.log(a);
console.log(b);
hi();
console.log(b);