📱 안드로이드 Android ~ Kotlin

[Kotlin/코틀린] 5 - 상속과 클래스 종류 (data 클래스, object 클래스, companion 클래스)

핑크빛연어 2022. 2. 4. 15:41

 

🚨 코틀린(Kotlin) 클래스의 상속과 생성자

- 코틀린(Kotlin) 의 클래스는 기본적으로 다른 클래스가 상속할 수 없다
- 다른 클래스에서 상속할 수 있게 선언하려면 open 키워드를 사용해야한다
- 상위클래스를 상속받은 하위 클래스의 생성자에서는 상위 클래스의 생성자를 호출해야 한다

open class Super1 {}  //Sub1 의 상위클래스 Super1
class Sub1: Super1() {}  //클래스의 매개변수가 없는 생성자 호출

open class Super2(name:String) {}  //Sub2,Sub3 의 상위클래스 Super2

//상위클래스를 상속받은 하위 클래스의 생성자에서는 상위 클래스의 생성자를 호출해야 한다
class Sub2(name: String): Super2(name) {}  //매개변수가 있는 상위 클래스의 생성자를 호출할 때는 매개변수 구성에 맞게 인자를 전달

class Sub3: Super2 {
    constructor(name: String): super(name) {}
}

 

 

🚨 코틀린(Kotlin) 의 클래스 종류

 

data 클래스

data class MyClass { .. } 형태로 사용 
- 자주 사용하는 데이터를 객체로 묶어준다
- VO 클래스를 편리하게 이용할 때 주로 사용
- data 클래스는 데이터를 다루는데 편리한 기능을 제공하는 것이 주목적
- 데이터 클래스에서 유용하게 사용되는 함수
 -> 객체의 데이터를 비교하는 equals() 함수, 객체의 데이터를 반환하는 toString() 함수

/* 일반 클래스 */
class NonDataClass(val name: String, val email: String, val age: Int) {}

/* 데이터 클래스 */
data class DataClass(val name: String, val email: String, val age: Int) {}

/* 데이터 클래스
* - equals() 함수 사용시 객체 자체를 비교하는 것이 아닌 객체의 데이터를 비교한다
* - 비교시 주생성자에 선언한 멤버 변수의 데이터만 비교 대상으로 삼는다
*  */
data class MyDataClass(
    val name: String,
    val email: String,
    val age: Int
) {  //주생성자에 선언한 멤버 변수의 데이터만 비교 대상으로 삼는다
    lateinit var address: String

    constructor(name: String, email: String, age: Int, address: String) : this(name, email, age) {
        this.address = address
    }
}


fun main() {
    val non1 = NonDataClass("eun", "a@a.com", 10)
    val non2 = NonDataClass("eun", "a@a.com", 10)
    println("non1.equals(non2) : ${non1.equals(non2)} ")  //객체 자체를 비교 => non1.equals(non2) : false
    println("NonDataClass > non1.toString : ${non1.toString()} ")  // => NonDataClass@64616ca2 

    val data1 = DataClass("eun", "a@a.com", 10)
    val data2 = DataClass("eun", "a@a.com", 10)
    println("data1.equals(data2) : ${data1.equals(data2)} ")  //객체의 데이터를 비교 => data1.equals(data2) : true
    println("DataClass > data1.toString : ${data1.toString()} ")  // => DataClass > data1.toString : DataClass(name=eun, email=a@a.com, age=10) 

    var obj1 = MyDataClass("eun", "a@a.com", 10, "seoul")
    var obj2 = MyDataClass("eun", "a@a.com", 10, "busan")
    println("obj1.equals(obj2) : ${obj1.equals(obj2)} ")  //객체의 데이터를 비교 => obj1.equals(obj2) : true
    println("MyDataClass > obj1.toString : ${obj1.toString()} ")  // => MyDataClass > obj1.toString : MyDataClass(name=eun, email=a@a.com, age=10) 
}

 

object 클래스

- 익명 클래스를 만들 목적으로 사용
- 클래스 이름이 없으므로 클래스를 선언하면서 동시에 객체를 생성
- 선언과 동시에 객체를 생성한다는 의미 => object 키워드 사용
- object { .. } 형태로 익명 클래스를 선언할 수 있지만 보통 타입까지 함꼐 입력해서 선언한다
- object: A { .. } 형태는 클래스를 A 타입으로 선언한 것
  -> A 가 클래스이면 A 클래스를 상속받은 하위 클래스를 익명으로 선언한 것
  -> A가 인터페이스면 A 인터페이스를 구현한 익명 클래스를 선언한 것
  -> object 객체를 A 타입으로 이용 할 수 있게 된 것이다

/* object 키워드로 익명 클래스를 선언
* - 클래스를 선언하자마자 객체가 생성되며 그 객체를 obj1 변수에 저장한다
* - object 키워드로 클래스를 선언했지만 타입을 명시하지 않아 kotlin 의 최상위 타입인 Any 로 취급한다
* */
val obj1 = object {
    var data = 10
    fun some() {
        println("obj1 > some() - data : $data ")
    }
}

open class Super {
    open var data = 10
    open fun some() {
        println("Super > some() - data : $data ")
    }
}

/* 타입을 지정한 object 클래스
* - Super 클래스를 상속받는다
* - obj2 객체를 이용해 Super 클래스에 선언된 멤버에 접근 가능
* */
val obj2 = object : Super() {
    override var data = 20
    override fun some() {
        super.some()
        println("obj2 > some() - data : $data ")
    }
}

fun main() {

    obj1.data = 20  //오류! - Any 타입 객체에는 data 이라는 멤버가 없어서 오류 발생
    obj1.some()  //오류! - Any 타입 객체에는 some() 이라는 멤버가 없어서 오류 발생

    obj2.data = 30  //성공!
    obj2.some()  //성공!
    // => Super > some() - data : 30
    // => obj2 > some() - data : 30

}

 

companion 클래스

- 멤버 변수나 함수를 클래스 이름으로 접근하고자 할 때 사용
- 객체를 생성하지 않고서도 클래스 이름으로 특정 멤버를 이용가능
- 클래스 내부에 companion object { .. } 형태로 선언하면 이 클래스를 감싸는 클래스 이름으로 멤버에 접근 가능

/* 일반 클래스의 멤버 접근 */
class MyClass1 {
    var data = 10
    fun some() {
        println("MyClass1 > data : $data ")
    }
}


/* 컴패니언 클래스의 멤버 접근
* - 클래스 이름으로 멤버에 접근할 수 있게 하려면 companion 키워드로 선언해야 한다
*  */
class MyClass2 {
    companion object {
        var data = 10
        fun some() {
            println("MyClass2 > data : $data ")
        }
    }
}

fun main() {
    val obj1 = MyClass1()
    obj1.data = 20
    obj1.some()  // => MyClass1 > data : 20
//    MyClass1.data = 20  // => 오류!
//    MyClass1.some()  // => 오류!

    MyClass2.data = 20  // => 성공!
    MyClass2.some()  // => 성공!  => MyClass2 > data : 20

}

 

감사합니다~:)

더보기
Kotlin/코틀린
728x90
반응형