클래스 상속 및 다형성 - swkim0128/PARA GitHub Wiki

1. 클래스 상속

기본 개념

  • 상속은 기존 클래스(부모 클래스)의 속성과 메서드를 새로운 클래스(자식 클래스)에서 사용할 수 있게 합니다.
  • open 키워드를 사용하여 상속 가능한 클래스를 정의합니다.

클래스 상속 문법

open class 부모클래스 {
    // 속성 및 메서드
}

class 자식클래스 : 부모클래스() {
    // 속성 및 메서드
}

예제: 클래스 상속

open class Animal {
    open fun sound() {
        println("동물이 소리를 냅니다.")
    }
}

class Dog : Animal() {
    override fun sound() {
        println("멍멍!")
    }
}

fun main() {
    val dog = Dog()
    dog.sound() // 출력: 멍멍!
}

super 키워드

  • 부모 클래스의 속성이나 메서드에 접근할 때 사용합니다.

예제

open class Animal {
    open fun sound() {
        println("동물이 소리를 냅니다.")
    }
}

class Dog : Animal() {
    override fun sound() {
        super.sound() // 부모 클래스의 메서드 호출
        println("멍멍!")
    }
}

fun main() {
    val dog = Dog()
    dog.sound()
}

출력:

동물이 소리를 냅니다.
멍멍!

생성자와 상속

  • 자식 클래스는 반드시 부모 클래스의 생성자를 호출해야 합니다.

예제: 생성자 상속

open class Animal(val name: String) {
    fun introduce() {
        println("저는 $name입니다.")
    }
}

class Dog(name: String) : Animal(name)

fun main() {
    val dog = Dog("Buddy")
    dog.introduce() // 출력: 저는 Buddy입니다.
}

2. 다형성 (Polymorphism)

  • 다형성은 객체가 여러 형태를 가질 수 있는 성질을 의미합니다.
  • 부모 클래스 타입으로 자식 클래스를 참조할 수 있습니다.

예제: 다형성

open class Animal {
    open fun sound() {
        println("동물이 소리를 냅니다.")
    }
}

class Dog : Animal() {
    override fun sound() {
        println("멍멍!")
    }
}

class Cat : Animal() {
    override fun sound() {
        println("야옹!")
    }
}

fun main() {
    val animals: List<Animal> = listOf(Dog(), Cat())

    for (animal in animals) {
        animal.sound()
    }
}

출력:

멍멍!
야옹!

타입 캐스팅

  • is 키워드로 객체 타입을 확인합니다.
  • as 키워드로 타입을 변환합니다.

예제

fun main() {
    val animal: Animal = Dog()

    if (animal is Dog) {
        animal.sound() // 출력: 멍멍!
    }

    val dog = animal as Dog
    dog.sound() // 출력: 멍멍!
}

3. 추상 클래스 (Abstract Class)

  • 추상 클래스는 인스턴스를 생성할 수 없으며, 반드시 상속을 통해 구현해야 합니다.
  • 추상 클래스는 abstract 키워드를 사용하여 정의합니다.
  • 추상 클래스 내의 추상 메서드는 구현하지 않아도 됩니다.

문법

abstract class 추상클래스 {
    abstract fun 추상메서드()
}

예제: 추상 클래스

abstract class Animal {
    abstract fun sound()

    fun sleep() {
        println("잠을 잡니다.")
    }
}

class Dog : Animal() {
    override fun sound() {
        println("멍멍!")
    }
}

fun main() {
    val dog = Dog()
    dog.sound() // 출력: 멍멍!
    dog.sleep() // 출력: 잠을 잡니다.
}

4. 인터페이스 (Interface)

  • 인터페이스는 클래스가 구현해야 할 동작을 정의합니다.
  • 다중 상속을 지원하며, 메서드 구현도 가능합니다.

문법

interface 인터페이스이름 {
    fun 메서드이름()
}

예제: 인터페이스 구현

interface Animal {
    fun sound()
}

class Dog : Animal {
    override fun sound() {
        println("멍멍!")
    }
}

class Cat : Animal {
    override fun sound() {
        println("야옹!")
    }
}

fun main() {
    val dog = Dog()
    val cat = Cat()

    dog.sound() // 출력: 멍멍!
    cat.sound() // 출력: 야옹!
}

5. 클래스 상속 vs 인터페이스

특징 클래스 상속 인터페이스
키워드 open 또는 abstract interface
다중 상속 불가능 가능
상태 (속성 포함) 상태(속성)를 가질 수 있음 상태(속성)를 가질 수 없음 (일반 메서드 제외)

요약

1. 상속:

  • open 키워드로 클래스와 메서드를 상속 가능하게 정의.
  • super 키워드로 부모 클래스 참조.

2. 다형성:

  • 부모 클래스 타입으로 자식 객체를 참조.
  • 타입 검사와 변환은 is와 as 키워드를 사용.

3. 추상 클래스:

  • 인스턴스화할 수 없으며, 상속받아 구현.

4. 인터페이스:

  • 다중 상속 가능하며, 동작(행위)을 정의.

코틀린의 상속과 다형성을 적절히 활용하면 코드의 재사용성과 확장성을 크게 높일 수 있습니다.

⚠️ **GitHub.com Fallback** ⚠️