JavaScript | 클래스

yuni·2022년 9월 30일
0

javascript

목록 보기
7/16
post-thumbnail

⇒ Class는 객체를 생성하기 위한 템플릿으로 객체지향프로그래밍에서 많이 사용되는 개념이다.
    Class를 정의하는 방법은 크게 class 표현식과 class 선언 방법이 있다.

ES6이후부터 클래스(Class)기반으로 객체지향 프로그래밍을 한다.

👁‍🗨 클래스(Class)

객체를 여러개 생성하는 경우,
생성자 함수( New Funtion() )와 모던 자바스크립트에 도입된 ES6의 클래스(class)라는 문법이 있다.

생성자 함수: 오래된 방법으로 더 이상 쓰이지 않음.

  • ES6 클래스는 class 키워드를 사용하여 정의
  • PascalCase로 표기
  • 객체의 기본 상태를 설정해주는 생성자 메서드 constructor()new에 의해 자동으로 호출되므로,
    특별한 절차 없이 객체를 초기화
    • constructor: 인스턴스를 생성하고 클래스 필드(생성자 함수에서 this에 추가한 프로퍼티)를 초기화하기 위한 특수한 메소드
    • constructor는 클래스 내에 한 개만 존재(그 이상일 경우 문법 에러(SyntaxError)가 발생)
    • 생략 가능(빈 객체 생성) - 클래스 필드를 초기화해야 한다면 생략X

📌 생성자함수 vs Class

생성자함수의 코드를 class의 코드로 변환해보자!

✔ 생성자함수

//생성자 함수
function User(first, last) {
  this.firstName = first;
  this.lastName = last;
  this.display = () => {
    console.log(`myname is ${this.last} ${this.first}`);
  };
  //return this //생략가능
}

//User : 생성자함수
const kim = new User('kim', 'yena');
const amy = new User('Amy', 'Clarke');

console.log(kim);
console.log(amy);

Class

class User {
  //생성자: new 키워드로 객체를 생성할때 호출되는 함수
  constructor(first, last) {
  // this는 클래스가 생성할 인스턴스를 가리킨다.
  // firstName, lastNam은 클래스 필드이다
    this.firstName = first;
    this.lastName = last;
  }
  display = () => {
    console.log(`myname is ${this.last} ${this.first}`);
  };
}

//인스턴스 생성
// kim은 User 클래스의 인스턴스이다.
const kim = new User('kim', 'yena');
const amy = new User('Amy', 'Clarke');

console.log(kim);
console.log(amy);

console.log(User.first);
User.display();
호출X

→ 클래스 자체에는 데이터가 채워져 있지 않으며, 템블릿이기 때문이다.
→ 생성된 인스턴스를 통해서 접근하고 호출해야 한다.

📌 정적 메소드 - static 키워드

  • 클래스를 위한 정적(static) 메서드를 정의 할때 static 키워드 사용
  • 정적 메소드는 클래스의 인스턴스가 아닌 클래스 이름으로 호출한다.
    따라서 클래스의 인스턴스를 생성하지 않아도 호출할 수 있다. (인스턴스화 없이 호출)
  • 클래스의 인스턴스에서는 호출 할 수 없다. (this사용 X)
  • Math 객체의 메소드처럼 애플리케이션 전역에서 사용할 유틸리티(utility) 함수를 생성할 때 주로 사용된다.

⇨ 클래스 별로 공통적이게 사용 or 만들어진 인스턴스 레벨에 참조 할 필요가 없을 경우

//static 정적 프로퍼티, 메서드
class User {
  static MAX_USER = 23;

  //생성자: new 키워드로 객체를 생성할때 호출되는 함수
  constructor(first, last) {
    this.firstName = first;
    this.lastName = last;
  }
  //클래스 레벨의 메소드
  static randomUser() {
    //this를 사용할 수 없다.
    return new User('Na', 'jinsu');
  }

  //인스턴스 레벨의 메소드
  display = () => {
    console.log(`myname is ${this.last} ${this.first}`);
  };
}

//클래스 레벨의 메소드(정적 메소드)는 클래스 이름으로 호출한다.
const jinsu = User.randomUser();
console.log(jinsu);
console.log(User.MAX_USER);

// kim은 User 클래스의 인스턴스이다.
const kim = new User('kim', 'yena');
const amy = new User('Amy', 'Clarke');

console.log(kim);
console.log(amy);

⇒ 호출

// 호출
User{
  display: [Function: display],
  firstName: 'Na',
  lastName: 'jinsu'
}
23
User {
  display: [Function: display],
  firstName: 'kim',
  lastName: 'yena'
}
User {
  display: [Function: display],
  firstName: 'Amy',
  lastName: 'Clarke'
}

→ class의 static함수는 만들어진 인스턴스안에는 들어있지 않는다.
→ class의 이름을 통해 접근하고 호출가능 하다. (ex: User.randomUser(); )

📌 클래스 필드(class field)

  • 프로퍼티 이름 = 값;
  • 클래스 내부의 캡슐화된 변수.
  • 클래스 필드의 선언과 초기화는 반드시 constructor 내부에서 실시
  • ES6의 클래스는 다른 객체지향 언어처럼 private, public, protected 키워드와 같은
    접근 제한자(access modifier)를 지원하지 않는다.
    • public : 기본적으로 적용(클래스의 인스턴스를 통해 클래스 외부에서 언제나 참조가능)
    • private : # 를 사용
                 내부에서는 사용이 가능, 외부에서는 사용이 불가능
class User {
  #first;
  #last;
  #country = 'korea';
  constructor(first, last) {
    this.#first = first; // 클래스 필드의 선언과 초기화 
    this.#last = last;
  }
  display = () => {
    console.log(`myname is ${this.#last} ${this.#first}`);
  };
}

const kim = new User('kim', 'yena');
//kim.#name = 'jin' -> #field는 외부에서 접근이 불가능
console.log(kim);

📌 getter와 setter

접근자 프로퍼티 (Accessor Property)

getter

  • 클래스 필드에 접근할 때마다 클래스 필드의 값을 조작하는 행위가 필요할 때 사용
  • 메소드 이름 앞에 get 키워드를 사용
  • 호출하는 것이 아니라 프로퍼티처럼 참조하는 형식(참조 시에 메소드 호출)
  • 반드시 무언가를 반환(retrun)해야 한다.

setter

  • 클래스 필드에 값을 할당할 때마다 클래스 필드의 값을 조작하는 행위가 필요할 때 사용
  • 메소드 이름 앞에 set 키워드를 사용
  • 호출하는 것이 아니라 프로퍼티처럼 값을 할당하는 형식(할당시에 메소드 호출)
//접근자 프로퍼티 (Accessor Property)
class Fruit {
  constructor(name, emoji) {
    this.name = name;
    this.emoji = emoji;
  }
  get print() {
    //getter은 반드시 반환해야 한다.
    return `${this.name}: ${this.emoji}`;
  }

  set color(value) {
    console.log(`color: `, value);
  }
}

const melon = new Fruit('melon', '🍈');
//클래스 필드 print에 접근하면 getter가 호출된다.
console.log(melon.print); //melon: 🍈

//클래스 필드 color에 값을 할당하면 setter가 호출된다.
melon.color = 'green';
console.log(melon.color); //color: green

📌 클래스 상속 - extends, spuer (Class Inheritance)

extends

  • 중복된 코드를 줄이고 코드 재사용에 좋다.
  • extends 키워드는 부모 클래스(base class)를 상속받는 자식 클래스(sub class)를 정의할 때 사용
//부모 클래스
class Fruit {
  constructor(color) {
    this.color = color;
  }
  big() {
    console.log('크다');
  }
  small() {
    console.log('작다');
  }
}

//자식 클래스 1
class Apple extends Fruit {}

const apple = new Apple('red');
console.log(apple); //Apple { color: 'red' }
apple.big(); //크다 -> Fruit의 속성과 함수에 접근가능

//자식 클래스 2
//상속 후  food() 추가
class Orange extends Fruit {
  food() {
    console.log('오렌지 케잌');
  }
  
 //*오버라이딩(overriding) : 자식클래스에서 다시 재정의
  big() {
    console.log('크기가 크다');
  }
}

const orange = new Orange('orange');
console.log(orange); //Orange { color: 'orange' }
orange.food(); //오렌지 케잌
orange.big(); //크기가 크다

*오버라이딩(overriding) : 부모 클래스가 가지고 있는 메소드를 자식 클래스가 재정의하여 사용하는 방식

spuer

  • super 키워드는 부모 클래스를 참조(Reference)할 때 또는 부모 클래스의 constructor를 호출할 때 사용한다.
//부모 클래스
class Fruit {
  constructor(color) {
    this.color = color;
  }
  big() {
    console.log('크다');
  }
  small() {
    console.log('작다');
  }
}

//자식 클래스 1
class Orange extends Fruit {
  constructor(color, farmName) {
    //super가 먼저 호출되어야 한다(아니면 참조 오류)
    //1. super 메소드는 부모 클래스의 constructor를 호출하면서 인수를 전달한다.
    super(color);
    this.farmName = farmName;
  }
  small() {
    //2. super 키워드는 부모 클래스(Base Class)에 대한 참조
    super.small();
    console.log('크기가 작다');
  }
}

const orange = new Orange('orange', '해피농장');
console.log(orange); //Orange { color: 'orange', farmName: '해피농장' }
orange.small(); // 작다, 크기가 작다

⇨ 1. super 메소드는 자식 클래스 내부에서 부모 클래스의 constructor를 호출하면서 인수를 전달한다.
       super가 먼저 호출되어야 한다. (아니면 참조 오류)
⇨ 2. super 키워드는 부모 클래스(Base Class)에 대한 참조. 부모 클래스의 필드 또는 메소드를 참조하기 위해 사용한다.

참고 및 출처
Classes - MDN
클래스와 기본 문법
Class - PoiemaWeb

profile
˗ˋˏϟˎˊ˗ 개발 지식 쌓기

0개의 댓글