[ JS ] Class

메이·2024년 5월 7일

JavaScript

목록 보기
10/12

🔎 class란?

class객체를 생성하기 위한 템플릿이다.
객체를 직접 작성해서 정의하고 생성할 수 있지만, 클래스로 만들어주면 여러 객체를 더 쉽게 만들 수 있다!

class를 통해서 원하는 구조의 객체 틀을 짜 놓고, 비슷한 모양의 객체를 찍어낼 수 있다.
(클래스 = 붕어빵 틀 / 객체 = 붕어빵 / 인스턴스 = 슈크림 붕어빵😜)


🔎 instance란?

class 에 소속된 개별적인 객체이다.
(객체를 실체화 시킨 것!! new Animal())

예를들어, User라는 클래스를 정의하고 Lee라는 객체를 생성할 경우,
Lee는 User의 인스턴스!


🔎 class를 왜 사용하나요?

ES6부터 추가된 class는 직관적으로 쉽게 코드를 읽을 수 있게 만들어줄 뿐만 아니라 작성하기도 쉽고,
class 기반 언어에 익숙한 개발자가 더 빠르게 적응할 수 있다.

// 객체 리터럴
const neo = {
    name: 'Neo',
    age: 22,
    getBirthYear() {
        const year = new Date().getFullYear()
        return year - this.age
    }
}
const evan = {
    name: 'Evan',
    age: 7
}

console.log(neo.getBirthYear())
console.log(evan.getBirthYear())

2002
Error..

// 객체 리터럴
const neo = {
    name: 'Neo',
    age: 22,
    getBirthYear() {
        const year = new Date().getFullYear()
        return year - this.age
    }
}
const evan = {
    name: 'Evan',
    age: 7,
    getBirthYear() {
      const year = new Date().getFullYear()
      return year - this.age
    }
}
console.log(neo.getBirthYear())
console.log(evan.getBirthYear())
console.log(neo.getBirthYear() === evan.getBirthYear())

2002
2017
false

  • 같은 코드를 가지고있는 함수가 총 두개가 만들어짐
  • 완전히 같은 함수인데 메모리에도 두개의 함수가 존재하게 됨 => 비효율적임

prototype

// 프로토타입
function User(name, age) {
  this.name = name
  this.age = age
}
function getBirthYear() {
  const year = new Date().getFullYear()
  return year - this.age
} // 각각의 객체 데이터에서 쓸 수 없는 형태임

const neo = new User('Neo', 22) // 생성자 함수
// 함수 데이터를 new라는 키워드와 함께 생성자 함수를 호출하면 객체데이터를 반환받을 수 있다 = 인스턴스
const evan = new User('Evan', 7)

console.log(neo)
console.log(evan)

User {name: 'Neo', age: 22}
User {name: 'Evan', age: 7}

// 프로토타입
function User(name, age) {
  this.name = name
  this.age = age
}
User.prototype.getBirthYear = function () {
  const year = new Date().getFullYear()
  return year - this.age
}


const neo = new User('Neo', 22) // 생성자 함수
// 함수 데이터를 new라는 키워드와 함께 생성자 함수를 호출하면 객체데이터를 반환받을 수 있다 = 인스턴스
const evan = new User('Evan', 7)

console.log(neo)
console.log(evan)
console.log(neo.getBirthYear())
console.log(evan.getBirthYear())
console.log(neo.getBirthYear() === evan.getBirthYear())

User {name: 'Neo', age: 22}
User {name: 'Evan', age: 7}
2002
2017
true

class

// 클래스
class User {
  constructor(name, age) {
    this.name = name
    this.age = age
  }
  getBirthYear() {
    const year = new Date().getFullYear()
    return year - this.age
  }
}

getter / setter

// 클래스 - Getter & Setter

class User {
  constructor(first, last) {
    this.firstName = first
    this.lastName = last
  }
  get fullName () {
    return `${this.firstName} ${this.lastName}`
  }// 함수를 속성처럼 사용하기 위해서 함수 앞에 get이라는 키워드를 붙여준다
  set fullName(value) {
    const names = value.split(' ') // ['Lewis', 'Park']
    this.firstName = names[0]
    this.lastName = names[1]
  }
}

const neo = ('Neo', 'Park')

//Get
console.log(neo.fullName)
// set
neo.fullName = 'Lewis Park'
console.log(neo)

정적 메소드(Static method)

  • 정적 메소드는 주로 클래스의 유틸리티(보조) 함수를 만들 때 사용한다.
  • 인스턴스와는 연결되지 않으며, 클래스 자체에서 호출해야 한다.

✍ 예제 1

const fruits = new Array('Apple', 'Banana', 'Cherry') // 생성자 함수 방식
// const fruits = ['Apple', 'Banana', 'Cherry'] // 리터럴 방식
// 리터럴 방식은 생성자 방식보다 더 간단하게, 기호를 통해서 데이터를 생성하는 것임

// fruits.includes('Apple') 데이터에서 직접 사용하는 메소드 : 프로토타입 메소드
// fruits.filter(item => item)
// fruits.push('Orange')

// 클레스의 프로토타입 속성에 등록된 함수(.first)는 생성자 함수로 만들어진
// 인스턴스(fruits)에서 빌려서 사용할 수 있다.

Array.prototype.first = function () {
  console.log(this)
  return this.map(item => item.slice(0, 1).toLowerCase())
} 
// first 라는 프로토타입 메소드를 만들게 됨
// 모든 배열 데이터는 first라는 메소드를 언제든지 사용할 수 있다


const newFruits = fruits.first()
console.log(newFruits)

console.log(Array.isArray(fruits))
console.log(Array.isArray(newFruits))

console.log(['Orange', 'Mango'].first())
  

['Apple', 'Banana', 'Cherry']
['a', 'b', 'c']

true
true

['Orange', 'Mango']
['o', 'm']

✍ 예제 2

class User {
  constructor(first, last) {
    this.firstName = first
    this.lastName = last
  }
  static isUser(user) {
    return user instanceof User
  } // 정적 메소드
}
// 변수 이름만 봤을 때 어떤게 User 인스턴스이고 단순 객체 리터럴로 만들어진 데이터인지
// 구분을 할 수 없기 때문에 isUser라는 메소드를 만듦

const neo = new User('Neo', 'Park') // neo가 this 키워드로 들어감
const evan = new User('Evan', 'Yang')
const lewis = {
  name: 'Lewis Lee',
  age: 72
}


console.log(neo)
console.log(evan)

console.log(User.isUser(neo))
console.log(User.isUser(evan))
console.log(User.isUser(lewis))
  

User {firstName: 'Neo', lastName: 'Park'}
User {firstName: 'Evan', lastName: 'Yang'}
true
true
false


상속(Inheritance)

  • 클래스의 속성과 메소드를 다른 클래스에게 확장(Extends)해 재사용하는 기능

✍ 예제 1

class A {
  constructor(a) {
    this.a = a
  }
}
class B extends A {
  constructor(a, b) {
    super(a)
    this.b = b
  }
}

const a = new A(1) // a가 this 키워드로 들어감
const b = new B(1, 2)

console.log(a)
console.log(b)

console.log(a instanceof A)
console.log(b instanceof A)

console.log(a instanceof B)
console.log(b instanceof B)

console.log(a instanceof Object)
console.log(b instanceof Object)

A {a: 1}
B {a: 1, b: 2}
true
true
false
true
true
true

✍ 예제 2

class User {
  constructor(name) {
    this.name = name
  }
  getName() {
    return this.name
  }
}
class Guest extends User {
  constructor(name) {
    super(name)
  }
}
class Member extends User {
  constructor(name) {
    super(name)
    this.private = true
  }
  getPrivate() {
    return this.private
  }
}
class Admin extends Member {
  constructor(name) {
    super(name)
    this.admin = true
  }
}

const neo = new Guest('Neo')
const evan = new Member('Evan')
const lewis = new Admin('Lewis')

console.log(neo)
console.log(evan)
console.log(lewis)

console.log(neo.constructor === Guest)
console.log(evan.constructor === Member)
console.log(lewis.constructor === User)

Guest { name: 'Neo' }
Member { name: 'Evan', private: true }
Admin { name: 'Lewis', private: true, admin: true }

true
true
false

profile
프론트엔드 개발자를 꿈꾸는 코린이₊⋆ ☾⋆⁺

0개의 댓글