티스토리 뷰
2.1 타입이란
2.1.1 자료형으로서의 타입
- 프로그래밍 언어에서 변수란 값을 저장할 수 있는 공간(컴퓨터의 메모리)이자 값을 가리키는 상징적인 이름이다.
- 변수에 저장할 수 있는 값의 종류는 프로그래밍 언어마다 다르다.
- 자바스크립트는 다음과 같은 7가지 데이터 타입(자료형)을 정의한다.
- undefined
- null
- Boolean
- String
- Symbol
- Numeric (Number 와 BigInt)
- Object
2.1.2 집합으로서의 타입
- 타입은 값이 가질 수 있는 유효한 범위의 집합을 말한다.
- 타입 시스템은 코드에서 사용되는 유효한 값의 범위를 제한해서 런타임에서 발생할 수 있는 유효하지 않은 값에 대한 에러를 방지해 준다.
2.1.3 정적 타입과 동적 타입
- 만약 자바스크립트만 사용했다면 변수와 값을 다룰 때 타입은 고려하지 않고 코드를 작성했을 수 있다.
- 그러나, 자바스크립트에도 분명히 타입은 존재한다!
- 다만, 개발자가 컴파일 이전에 타입을 직접 정의해 줄 필요가 없었을 뿐이다!
- 타입을 결정하는 시점에 따라 타입을 정적 타입(static type)과 동적 타입(dynamic type)으로 분류할 수 있다.
- 정적 타입 : 모든 변수의 타입이 컴파일 타임에 결정. (ex. C, 자바, 타입스크립트)
- 컴파일 타임에 타입 에러를 발견할 수 있기에 프로그램의 안정성 보장 가능.
- 동적 타입 : 변수 타입이 런타임에 결정. (ex. 파이썬, 자바스크립트)
- 프로그램을 실행할 때 타입 에러가 발견되기에 개발 과정에서는 자유롭게 코드를 작성할 수 있지만, 언제 프로그램에 오류가 생길지 모르는 불안감.
- 정적 타입 : 모든 변수의 타입이 컴파일 타임에 결정. (ex. C, 자바, 타입스크립트)
2.1.4 강타입과 약타입
- 암묵적 타입 변환(implicit conversion) : 개발자가 의도적으로 타입을 명시하거나 바꾸지 않았는데도 컴파일러 또는 엔진 등에 의해서 런타임에 타입이 자동으로 변경되는 것
- 암묵적 타입 변환 여부에 따라 타입 시스템을 강타입(strongly type) 과 약타입(weekly type) 으로 분류할 수 있다.
- 강타입 : 서로 다른 타입을 갖는 값끼리 연산 시, 컴파일러 또는 인터프리터에서 에러 발생.
- 약타입 : 서로 다른 타입을 갖는 값끼리 연산 시, 컴파일러 또는 인터프리터가 내부적으로 판단해서 특정 값의 타입을 변환하여 연산을 수행한 후 값을 도출.
- 암묵적 타입 변환은 개발자가 명시적으로 타입을 변환하지 않아도 다른 데이터 타입끼리 연산을 진행할 수 있는 편리함을 제공하지만, 작성자의 의도와 다르게 동작할 수 있기에 예기치 못한 오류가 발생할 가능성도 높아진다.
2.1.5 컴파일 방식
- 컴파일의 일반적인 의미는 사람이 이해할 수 있는 방식으로 작성한 코드를 컴퓨터가 이해할 수 있는 기계어로 바꿔주는 과정을 말한다.
- 그러나, 타입스크립의 컴파일 결과물은 여전히 사람이 이해할 수 있는 자바스크립트 파일이다.
(다른 타입의 개념을 사용하는 언어와는 구별되는 특징을 가지고 있다.) - 타입스크립트가 탄생한 이유는 자바스크립트의 컴파일 타임에 런타임 에러를 사전에 잡아내기 위한 것이다.
2.2 타입스크립트의 타입 시스템
2.2.1 타입 애너테이션 방식
- 타입 애너테이션(type annotation) 이란, 변수나 상수 혹은 함수의 인자와 반환 값에 타입을 명시적으로 선언해서 어떤 타입 값이 저장될 것인지를 컴파일에 직접 알려주는 문법이다.
2.2.2 구조적 타이핑
- 타입을 사용하는 여러 프로그래밍 언어에서 값이나 객체는 하나의 구체적인 타입을 가지고 있다.
- 명목적으로 구체화한 타입 시스템이라 부른다. (nominal reified type systems)
- 서로 다른 클래스끼리 명확한 상속 관계나 공통으로 가지고 있는 인터페이스가 없다면 타입은 서로 호환되지 않는다.
- 그러나, 타입스크립트는 이름으로 타입을 구분하는 명목적인 타입 언어의 특징과 달리 구조로 타입을 구분한다.
- 구조적 타이핑(structural type system) 이라고 한다.
2.2.3 구조적 서브 타이핑
- 객체가 가지고 있는 속성(프로퍼티)을 바탕으로 타입을 구분하는 것이다.
- 이름이 다른 객체라도 가진 속성이 동일하다면 타입스크립트 서로 호환이 가능한 동일한 타입으로 여긴다.
- 타입스크립트의 서브 타이핑, 즉 타입의 상속 역시 구조적 타이핑을 기반으로 하고 있다.
- 서로 다른 두 타입 간의 호환성은 오로지 타입 내부의 구조에 의해 결정된다.
2.2.4 자바스크립트를 닮은 타입스크립트
- 명목적 타이핑의 경우, 이름으로 타입을 구분하기에 구조가 같더라도 이름이 다르다면 다른 타입으로 취급한다.
- 자바스크립트는 본질적으로 덕 타이핑을 기반으로 한다.
- 덕 타이핑 : 어떤 함수의 매개변숫값이 올바르게 주어진다면 그 값이 어떻게 만들어졌는지 신경 쓰지 않고 사용한다는 개념.
- "만약 어떤 새가 오리처럼 걷고, 헤엄치며 꽥꽥 거리는 소리를 낸다면 나는 오리라고 부를 것이다."
- 즉, 객체가 어떻게 만들어졌는 지 상관없이 원하는 동작을 하게 하면 신경쓰지 않는다는 것을 의미
- 덕 타이핑 : 어떤 함수의 매개변숫값이 올바르게 주어진다면 그 값이 어떻게 만들어졌는지 신경 쓰지 않고 사용한다는 개념.
- 타입스크립트는 이런 동작을 모델링하여 명시적인 이름을 가지고 타입을 구분하는 대신 객체나 함수가 가진 구조적 특징을 기반으로 타이핑하는 방식을 택했다.
- 덕 타이핑은 런타임에 타입을 검사하고 구조적 타이핑은 컴파일 타임에 타입 체커가 타입을 검사한다.
2.2.5 값 vs 타입
- 타입스크립트는 타입이라는 개념이 등장하며 :type 형태로 타입을 명시한다.
- 혹은 type이나 interface 키워드로 커스텀 타입을 정의할 수도 있다.
- 값과 타입의 공간의 이름은 서로 충돌하지 않기에 타입과 변수를 같은 이름으로 정의할 수 있는데 타입스크립트가 자바스크립트의 슈퍼셋인 것과 관련이 있다.
- 타입 스크립트 문법인 type으로 선언한 내용은 자바스크립트 런타임에서 제거되기에 값과 타입의 공간은 서로 충돌하지 않는다.
- 값과 타입 공간에 동시에 존재하는 심볼도 있다.
- 대표적으로 클래스와 enum이다.
- 타입스크립트에서 클래스는 값과 타입 공간 모두에 포함될 수 있다.
- 클래스는 타입 애너테이션으로 사용할 수 있지만 런타임에서 객체로 변환되어 자바스크립트의 값으로 사용
- enum 역시, 런타임에 객체로 변환되는 값이다.
- 클래스처럼 타입 공간에서 타입을 제한하는 역할을 하지만 자바스크립트 런타임에서 실제로 값으로도 사용될 수 있다.
더보기
1. TypeScript enum 선언
enum fruit {
Apple,
Banana,
Orange
}
이는 내부적으로 Apple = 0, Banana = 1, Orange = 2와 같은 숫자 열거형(Number Enum)으로 동작
2. JavaScript 컴파일 결과 분석
TypeScript는 위의 enum을 아래와 같이 컴파일합니다:
var fruit;
(function (fruit) {
fruit[fruit["Apple"] = 0] = "Apple";
fruit[fruit["Banana"] = 1] = "Banana";
fruit[fruit["Orange"] = 2] = "Orange";
})(fruit || (fruit = {}));
① 즉시 실행 함수 (IIFE, Immediately Invoked Function Expression)
(function (fruit) { ... })(fruit || (fruit = {}));
- fruit이라는 변수를 undefined가 아닌 객체로 초기화하기 위해 IIFE를 사용
- fruit || (fruit = {})는 fruit이 이미 정의되어 있다면 그대로 사용하고, 없으면 빈 객체 {}로 초기화
② 숫자 → 문자열 매핑
fruit[fruit["Apple"] = 0] = "Apple";
- fruit["Apple"] = 0 → fruit 객체에 "Apple"이라는 키로 0을 저장
- fruit[0] = "Apple" → 숫자 0을 키로 "Apple"을 저장
즉, 이 과정을 통해 fruit 객체는 아래처럼 구성
{
"Apple": 0,
"Banana": 1,
"Orange": 2,
0: "Apple",
1: "Banana",
2: "Orange"
}
이렇게 하면 양방향 매핑이 가능
console.log(fruit.Apple); // 0
console.log(fruit[0]); // "Apple"
즉, fruit.Apple을 통해 0을 얻을 수도 있고, fruit[0]을 통해 "Apple"을 얻을 수도 있는 구조
2.2.6 타입을 확인하는 방법
- 타입스크립트에서 typeof, instanceof 그리고 타입 단언을 사용해 타입을 확인할 수 있다.
- typeof : 연산하기 전에 피연산자의 데이터 타입을 나타내는 문자열 반환
- typeof 연산자도 값에서 쓰일 때와 타입에서 쓰일 때의 역할이 다르다.
- typeof : 연산하기 전에 피연산자의 데이터 타입을 나타내는 문자열 반환
- instanceof 연산자를 사용하면 프로토타입 체이닝 어딘가에 생성자의 프로토타입 속성이 존재하는지 판단할 수 있다.
- as 키워드를 사용해 타입을 강제할 수도 있다.
2.3 원시 타입
2.3.1 boolean
- 오직 true와 false 값만 할당할 수 있는 boolean 타입이다.
2.3.2 undefined
- 값이 아직 할당/정의되지 않았다는 의미의 타입으로 undefined 값만 할당할 수 있다.
- 초기화되어 있지 않거나 존재하지 않음을 나타낸다.
2.3.3 null
- 보통 빈 값을 할당해야 할 때 null을 사용한다.
- 명시적/의도적으로 값이 아직 비어있을 수 있음을 보여준다.
2.3.4 number
- 자바스크립트의 숫자에 해당하는 모든 원시 값을 할당할 수 있다.
- NaN (Not a number), Infinity 도 포함된다.
2.3.5 bigInt
- ES2020에서 도입된 타입으로 타입스크립트 3.2 버전부터 사용 가능
- Number.MAX_SAFE_INTEGER(2^53-1) 넘어가는 수를 처리할 수 있다.
- number 타입과 엄연히 다른 타입이기에 상호 작용은 불가능하다.
2.3.6 string
- 문자열을 할당할 수 있는 타입이다.
- 공백, ', ", ` 으로 감싼 템플릿 리터럴 문법도 있다.
2.3.7 symbol
- ES2015에서 도입된 타입으로 Symbol() 함수를 사용하면 어떤 값과도 중복되지 않는 유일한 값을 생성할 수 있게 된다.
2.4 객체 타입
- 7가지 원시 타입에 속하지 않는 값은 모두 객체 타입으로 분류할 수 있다.
2.4.1 object
- object 타입은 객체에 해당하는 모든 타입 값을 유동적으로 할당할 수 있어 정적 타이핑의 의미가 크게 퇴색되어 가급적 사용하지 말도록 권장된다.
- 원시타입은 object 타입에 속하지 않는다.
4.2.2 {}
- 타입스크립트에서는 객체를 타이핑할 때도 중괄호를 쓸 수 있으며, 중괄호 안에 객체의 속성 타입을 지정해 주는 식으로 사용한다.
- {} 타입으로 지정된 객체에는 어떤 값도 속성으로 할당할 수 없다.
- 사실, 빈 객체 타입을 지정하기 위해서는 유틸리티 타입으로 Record <string, never>처럼 사용하는 것이 바람직하다.
2.4.3 array
- 타입스크립트에서는 배열을 array라는 별도 타입으로 다룬다.
- Array 키워드로 선언하거나 대괄호[]를 사용해서 선언하는 방법이 있다.
- 튜플은 대괄호 내부에는 선언 시점에 지정해 준 타입 값만 할당할 수 있으며, 원소 개수도 타입 선언 시점에 미리 정해진다.
2.4.4 type과 interface 키워드
- 보통 object 타입을 쓰지 않고, 객체를 타이핑하기 위해 type, interface 키워드를 사용한다.
2.4.5 function
- 함수를 별도 함수 타입으로 지정할 수 있다.
- 유의해야 할 점
- 자바스크립트에서 typeof 연산자로 확인한 function이라는 키워드 자체를 타입으로 사용하지 않는다.
- 함수는 매개변수 목록을 받을 수 있는데 타입스크립트에서는 매개변수도 별도 타입으로 지정해야 한다.
- 함수가 반환하는 값이 있다면 반환 값에 대한 타이핑도 필요하다.
- 함수 타입을 정의할 때 호출 시그니처(call signature)를 사용한다.
- 호출 시그니처는 함수의 매개변수와 반환 값의 타입을 명시하는 역할을 한다.
- type add = (a: number, b: number) => number;
- 호출 시그니처는 함수의 매개변수와 반환 값의 타입을 명시하는 역할을 한다.
'study > typescript' 카테고리의 다른 글
우아한 타입스크립트 6장 타입스크립트 컴파일 (0) | 2025.02.23 |
---|---|
우아한 타입스크립트 5장 타입 활용하기 (0) | 2025.02.23 |
우아한 타입스크립트 4장 타입 확장하기 (0) | 2025.02.09 |
우아한 타입스크립트 3장 고급 타입 (1) | 2025.02.03 |
공지사항
최근에 올라온 글
최근에 달린 댓글
- Total
- Today
- Yesterday
링크
TAG
- homebrew
- 웹 스크래핑
- 스파르타코딩클럽 #비전공자코딩 #아이디어 #개발자멘토 #르탄즈 1기
- 내일배움단
- 르탄즈1기
- 크롤링
- 스파르타 코딩클럽
- 타입스크립트파일
- 공부하자...
- 1시간만에끝내는직장인코딩용어해설
- 타입확장하기
- 개발자멘토
- DOIT
- 코딩
- ios앱개발
- mongodb
- 우아한타입스크립트
- 비전공자코딩
- 내일배움카드
- 코딩교육
- 아이디어
- javascript
- Selenium
- 스파르타코딩클럽
- iOS 앱개발 기초반
- IOS
- 타입스크립트
- 스파르타코딩클럽후기
- 타입활용
- 개발일지
일 | 월 | 화 | 수 | 목 | 금 | 토 |
---|---|---|---|---|---|---|
1 | 2 | 3 | 4 | 5 | ||
6 | 7 | 8 | 9 | 10 | 11 | 12 |
13 | 14 | 15 | 16 | 17 | 18 | 19 |
20 | 21 | 22 | 23 | 24 | 25 | 26 |
27 | 28 | 29 | 30 | 31 |
글 보관함