ㅇㅇㅈ Blog

프론트엔드 수행중

0%

ts-01

  • private

    • 정의된 클래스 내에서만 접근 가능
    • 상속받는 클래스에서는 접근 불가
  • protected

    • private와 다른 점은 해당 클래스뿐만 아니라 확장하는 모든 클래스에서도 사용 가능
  • static

    • 정적 속성은 인스턴스에서 유효하지 않는다
    • this로 접근 불가, 클래스 이름으로 접근해야 함
1
2
3
4
5
6
7
8
9
abstract class Department {
static fiscalYear = 2020;

constructor(protected readonly id: string, public name: string) {
this.id = id;
console.log(this.fiscalYear); // 에러 발생 this는 Department 클래스를 기반으로 생성된 인스턴스를 참조하기 때문
console.log(Department.fiscalYear); // 올바른 접근
}
}
  • implements
    • 클래스가 특정 interface의 조건을 만족하는지 체크하기 위해 사용
    • 쉼표로 여러개의 interface를 implements 할 수 있다
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
interface ValidUser {
user: string;
}

interface ediable {
eat: () => boolean;
}

class Pserson implements ValidUser, ediable {
user: string;
constructor(n: string) {
this.user = n;
}

eat() {}
}
  • type 확장
1
2
3
4
5
6
7
8
9
10
11
12
13
14
type Admin = {
// interface로 만들어도 된다
name: string;
privileges: string[];
};

type Employee = {
// interface로 만들어도 된다
name: string;
startData: Date;
};

type ElevatedEmployee = Admin & Employee;
interface ElevatedEmployee extends Admin, Employee {}
  • intersection
1
2
3
4
5
type Combinable = string | number;
type Numeric = number | boolean;

type Universal = Combinable & Numeric;
// Universal은 number type이 된다
  • type guard
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
type UnknownEmployee = Employee | Admin;

function printEmployeeInformation(emp: UnknownEmployee) {
console.log("Name: " + emp.name);

console.log("Privileages" + emp.privileges); // Err 발생 Employee 타입에 privileges가 없기때문이다

if (typeof emp === "object") {
} // typeof emp는 object이기때문에 typeof키워드로 타입가드를 할 수 없다

if (typeof emp === "Employee") {
} // 이 if문은 JS에서 런타임때 동작하기때문에 type인 Employee로 조건을 구할 수 없다

if ("privileges" in emp) {
// privileges가 emp의 속성인지 in으로 확인 할 수 있다
console.log("Privileages" + emp.privileges);
// 정상 동작
}
}
  • function overloading
1
2
3
4
5
6
7
8
9
10
11
12
13
// 함수가 반환타입을 정확히 알지 못할때 오버로드를 통해 정확히 알 수 있게 해준다
function add(a: number, b: number): number;
function add(a: string, b: string): string;
function add(a: string, b: number): string;
function add(a: number, b: string): string;
function add(a: Combinable, b: Combinable) {
if (typeof a === "string" || typeof b === "string") {
return a.toString() + b.toString();
}
return a + b;
}
const result = add("Max", "Schwarz");
result.split;
  • ?? null undefined
1
2
3
4
const userInput = "";
const storedData = userInput ?? "DEFAULT";
console.log(storedData);
// null 이나 undefined 일때만 DEFAULT가 출력된다
  • generic
스크린샷 2022-08-30 오전 3 57 53

제네릭을 이용해 objA의 타입을 추론한다.
Object.assign으로 objAobjB를 합치려는데 에러발생
objA 타입 추론을 {}로 하고 있다.

스크린샷 2022-08-30 오전 4 03 08

스프레드 문법으로 바꿔 줬더니 에러는 사라진다.

하지만 문제점은

스크린샷 2022-08-30 오전 4 04 56

매개변수로 object가 아닌 number타입을 넣어도 에러가 발생하지 않는다.

제약조건을 줘서 object타입이 아니면 에러가 발생하게 해준다

스크린샷 2022-08-30 오전 4 07 50
  • class에서 제네릭
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
class DataStorage<T> {
private data: T[] = [];

addItem(item: T) {
this.data.push(item);
}

removeItem(item: T) {
if (this.data.indexOf(item) === -1) {
return;
}
this.data.splice(this.data.indexOf(item), 1);
}

getitems() {
return [...this.data];
}
}
1
2
3
4
5
const textStorage = new DataStorage<string>();
textStorage.addItem('Max');
textStorage.addItem('Manu');
textStorage.removeItem('Manu');
console.log(textStorage.getitems());

데이터가 원시타입에서는 문제 없이 동작 한다

1
2
3
4
5
const objStorage = new DataStorage<object>();
objStorage.addItem({ name: 'Max' });
objStorage.addItem({ name: 'Manu' });
objStorage.removeItem({ name: 'Max' });
console.log(objStorage.getitems());

하지만 데이터가 참조타입일때는 문제가 발생한다.

Max를 지웠지만 Max가 그대로 출력된다.

1
2
3
4
5
6
7
8
const maxObj = { name: 'max' };
const objStorage = new DataStorage<object>();
objStorage.addItem(maxObj);
objStorage.addItem({ name: 'Manu' });

objStorage.removeItem(maxObj);
console.log(objStorage.getitems());

이런식으로 객체를 변수에 담아 삭제하면 참조주소를 찾아 그 객체를 지우긴 한다.