최신 ECMAScript 표준을 따르는 자바스크립트는 다음과 같은 7가지 데이터 타입을 정의.
이와 같은 유형을 데이터 타입 또는 자료형이라고 한다.
※컴파일타임과 런타임
개발자가 작성한 소스코드를 실행하려면 몇 가지 과정을 거쳐야 하는데 시점에 따라 컴파일타임과 런타임으로 구분할 수 있다. 기계가 소스코드를 이해할 수 있도록 기계어로 변환되는 시점을 컴파일타임이라고 하며 이후 변환된 파일이 메모리에 적재되어 실행되는 시점을 런타임이라고 부름.
개발자가 의도적으로 타입을 명시하거나 바꾸지 않았는데도 컴파일러 또는 엔진 등에 의해서 런타임에 타입이 자동으로 변경되는 것을 암묵적 타입 변환
암묵적 타입 변환 여부에 따라 타입 시스템을 강타입과 약타입으로 분류
강타입 특징을 가진 언어에서는 서로 다른 타입을 갖는 값끼리 연산을 시도하면 컴파일러 또는 인터프리터에서 에러가 발생
약타입 특정을 갖는 언어에서 서로 다른 타입을 갖는 값끼리 연산할 때는 컴파일러 또는 인터프리터가 내부적으로 판단해서 특정값의 타입을 변환하여 연산을 수행한 후 값을 도출
타입 검사기가 프로그램에 타입을 할당하는 데 사용하는 규칙 집합을 타임 시스템이라고 함.
타입 애너테이션이란 변수나 상수 혹은 함수의 인자와 반환 값에 타입을 명시적으로 선언해서 어떤 타입 값이 저장될 것인지를 컴파일러에 직접 알려주는 문법
타입을 사용하는 여러 프로그래밍 언어에서 값이나 객체는 하나의 구체적인 타입을 가지고 있다. 타입은 이름으로 구분되며 컴파일타임 이후에도 남아있다. 이것을 명목적으로 구체화한 타입시스템이라고 함.
또한 서로 다른 클래스끼리 명확한 상속 관계나 공통으로 가지고 있는 인터페이스가 없다면 타입은 서로 호환되지 않는다.
그러나 타입스크립트에서 타입을 구분하는 방식은 조금 다르다. 이름으로 타입을 구분하는 명목적인 타입 언어의 특징과 달리 타입스크립트는 구조로 타입을 구분 이것을 구조적 타이핑이라고 함.
타입스크립트에서는 특정 값이 string 또는 number타입을 동시에 가질 수 있다.
type stringOrNumber = string | number
이처럼 집합으로 나타낼 수 있는 타입스크립트의 타입 시스템을 지탱하고 잇는 개념이 바로 구조적 서브 타이핑
구조적 서브 타이핑이란?
객체가 가지고 있는 속성(프로퍼티)을 바탕으로 타입을 구분하는 것이다. 이름이 다른 객체라도 가진 속성이 동일하다면 타입스크립트는 서로 호환이 가능한 동일 타입
명목적 타이핑은 타입의 동일성을 확인하는 과정에서 구조적 타이핑에 비해 조금 더 안전하다. 개발자가 의도한 타입이 아니라면 변수에 타입을 명시하는 과정에서 에러를 내뱉기때문.
즉 객체의 속성을 다른 객체의 속성과 호환되지 않도록 하여 안전성을 추구.
그런데도 타입스크립트가 구조적 타이핑을 채택한 이유는 타입스크립트가 자바스크립트를 모델링한 언어.
자바스크립트는 본질적으로 덕 타이핑을 기반
덕 타이핑은 어떤 함수의 매개변숫값이 올바르게 주어진다면 그 값이 어떻게 만들어졌는지 신경 쓰지 않고 사용한다는 개념
덕 타이핑과 구조적 타이핑의 차이는 타입을 검사한 시점에 있다. 덕 타이핑은 런타임에 타입을 검사한다. 자바스크립트는 덕 타이핑 언어다. 구조적 타이핑은 컴파일타임에 타입체커가 타입을 검사한다.
덕 타이핑은 주로 동적 타이핑에서 구조적 타이핑은 정적 타이핑에서 사용된다.
※ 덕 타이핑
어떤 타입에 부합하는 변수와 메서드를 가지고 있는 경우 해당 타입에 속하는 것으로 간주하는 방식
" 만약 어떤 새가 오리처럼 걷고, 헤엄치며 꽥꽥거리는 소리를 낸다면 나는 그 새를 오리라고 부를 것"
※ any 타입
타입스크립트에서 any 타입은 타입스크립트 내 모든 타입의 종류를 포함하는 가장 상위 타입으로 어떤 값이든 할당할 수 있다. 단, 타입스크립트 컴파일 옵션인 noImplicitAny 값이 true일 때는 에러가 발생한다. noImplicitAny는 타입 애너테이션이 없을 때 변수가 any 타입으로 추론되는 것을 허락하지 않는다. 타입스립트로 코드를 작성할 때는 tsconfig의 noImplicitAny옵션을 true로 설정하는 게 좋다.
type Person ={
name:string;
age:number;
}
interface Person {
name:string;
age:number;
}
값 공간과 타입 공간의 이름은 서로 충돌하지 않기 때문에 타입과 변수를 같은 이름으로 정의 할 수 있는데 타입 스크립트가 자바스크립트의 슈퍼셋인 것과 관련이 있다. 타입스크립트 문법인 type으로 선언한 내용은 자바스크립트 런타임에서 제거되기 때문에 값 공간과 타입 공간은 서로 충돌하지 않는다.
class Developer {
name:string;
domain:string;
constructor(name:string,domain:string){
this.name = name;
this.domain = domain
}
}
const me:Developer = new Developer("zig","frontend")
※ 원시 값과 원시 래퍼 객체
앞서 자바스크립트의 내장 타입을 파스칼 표기법으로 표기.
타입스크립트에서는 소문자로 표기.
자바스크립트는 컴파일 시점에 타입스크립트의 타입 시스템이 적용되지 않으므로 타입 스크립트와 구별하기 위해 소문자로 표기하지 않았다. 타입을 파스칼 표기법으로 표기하면 자바스크립트에서 이것을 원시 래퍼 객체라고 부른다. null과 undefined를 제외한 모든 원시 값은 해당 원시 값을 래퍼 객체라고 부른다.
오직 ture와 false 값만 할당할 수 있는 boolean 타입
정의되지 않았다는 의미의 타입으로 오직 undefined 값만 할당할 수 있다. 일반적으로 초기화되지 않는 값을 의미.
오직 null만 할당할 수 있음.
자바스크립트의 숫자에 해당하는 모든 원시 값을 할당할 수 있다.
자바스크립트에서 숫자에 해당하는 원시 값 중 NaN이나 Infinity도 포함 됨.
NaN은 Not A Number의 줄임말로 숫자가 아님을 나타냄.
Infinity는 무한대를 나타냄.
ES2020에 새롭게 도입된 데이터 타입으로 타입스크립트 3.2 버전부터 사용할 수 있음. 이전 자바스크립트에서는 가장 큰수인 Number.MAX_SAFE_INTEGER(2^53 -1)를 넘어가는 값을 처리할 수 없었는데 bigint를 사용하면 이보다 큰 수를 처리할 수 있다.
문자열을 할당할 수 있는 타입
symbol()을 사용하면 어떤 값과도 중복되지 않는 유일한 값을 생성
자바스크립트 객체의 정의 맞게 이에 대응하는 타입스크립트 타입 시스템은 object 타입.
사용을 권장하지 않는다.
자바스크립트에서 객체 리터럴 방식으로 객체를 생성할 때 사용한다.
타입스크립트에서 객체를 타이핑할 때도 중괄호를 쓸 수 있는데, 중괄호 안에 객체의 속성 타입을 지정해주는 식으로사용한다. 객체가 중괄호 안에서 선언된 구조와 일치해야 함.
타입스크립트에서는 배열을 array라는 별도 타입을 다룬다. 타입스크립트 배열 타입은 하나의 타입 값만 가질 수 있다는 점에서 자바스크립트 배열보다 조금 더 엄격.
타입스크립트에서 배열 타입을 선언하는 방식은 Array 키워드로 선언하거나 대괄호를 사용해서 선언하는 방법이 있다. 두 방식은 같은 방식이다.
주의 할 점은 튜플 타입도 대괄호를 사용하여 선언한다는 것.
배열과 유사하지만 튜플의 대괄호 내부에는 선언 시점에 지정해준 타입 값만 할당할 수 있다.
함수도 일종의 객체로 간주하지만 typeof 연산자로 함수 타입을 출력해보면 자바스크립트는 함수를 function이라는 별도 타입으로 분류한다.
function add(a,b){
return a+b
}
console.log(typeof add) //function
주의 할 사항
1. 자바스크립트에서 typeof 연산자로 확인한 function이라는 키워드 자체를 타입으로 사용하지 않는다.
2. 함수는 매개변수 목록을 받을 수 있는데 타입스크립트에서는 매개변수도 별도 타입으로 지정해야 함.
다음은 이러한 주의 사항을 모두 적용한 함수의 예시. 마지막으로 함수가 반환하는 값이 있다면 반환 값에 대한 타이핑도 필요하다.
function add(a:number,b:number):number{
return a+b
}
※ 호출 시그니처
타입스크립트에서 함수 타입을 정의할 때 사용하는 문법. 함수 타입은 해당 함수가 받는 매개변수와 반환하는 값의 타입으로 결종. 호출 시그니처는 이러한 함수의 매개변수와 반환 값의 타입을 명시하는 역할을 함.
type add = (a:number,b:number)=>number;
호출 시그니처를 들여다보면 자바스크립트의 화살표 함수와 맥락이 유사핟.
일반적으로 자바스크립트에서는 함수를 작성할 때 function 키워드를 사용해서 작동하거나 화살표 함수 방식으로 작성한다. 반면 타입스크립트에서는 함수 자체의 타입을 명시할 때는 화살표 함수 방식으로만 호출 시그니처를 정의.