코틀린 객체지향-3(클래스 상속 + 클래스 종류)

Bang!·2022년 1월 13일
0

Android(코틀린)

목록 보기
4/15
post-thumbnail

관련 코드 링크!(Github code link)

04-02 클래스를 재사용하는 상속
상속과 생성자

  • 클래스를 선언할 때 다른 클래스를 참조하는 것은 바로 상속(inheritance)!!

  • Koltin 에서는 클래스를 상속받으려면 콜론(:)과 함께 상속받을 클래스 이름을 입력한다

  • 예시) (클래스 상속 형식)
    open class Super{ //상속할 수 있게 open 키워드 이용
    }
    class Sub: Super(){ //Super를 상속받아 Sub 클래스 선언
    }

  • 기본 지식:
    ▪ 상속 대상 클래스는 상위 클래스, 상속받는 클래스는 하위 클래스

  • 코틀린에서는 class Super { } 처럼 클래스를 선언하면 다른 클래스에서 Super 클래스를 상속할 수 없음

  • 만약 다른 클래스에서 상속할 수 있게 선언하면 open 키워드를 사용한다
    ▪ 즉, open class Super { } 라고 선언하면 Super 클래스의 상속 허용

  • 하위 클래스를 선언할 때는 이름 뒤에 콜론(:)을 입력하고 상속받을 상위 클래스 이름을 입력
    ▪ `class Sub: Super() { } 코드는 Super 클래스를 상속받아 Sub클래스를 선언한 구문이다

  • 상위 클래스를 상속받은 하위 클래스의 생성자에서는 상위 클래스의 생성자를 호출해야 한다

  • 예)
    ▪ class Sub:Super { } 코드애서 Super()는 Super 클래스를 상속받으면서 클래스의 매개변수가 없는 생성자를 호출한다
    ▪ 만약 상위 클래스에 생성자가 있거나 생성자를 호출할 때는 다음처럼 해야한다
    ▪ 예1)
    //매개변수가 있는 상위 클래스의 생성자 호출
    open class Super(name:String){
    }
    class Sub(name:String): Super(name){
    }
    ▪ 예2)
    //하위 클래스에 보조 생성자만 있는 경우 상위 클래스의 생성자 호출
    open class Super(name:String){
    }
    class Sub(name:String): Super(name){
    }

오버라이딩 - 재정의

  • 기본 지식:
    ▪ 상위 클래스에 선언된 변수나 함수를 같은 이름으로 하위 클래스에서 다시 서언하는게 => 오버라이딩
    ▪ 오버라딩 예)
    open class Super{
    open var someData = 10
    open fun superClassfunc(){
    println("fun superClassfunc printing: $someData")
    }
    }
    class Sub: Super() {
    override var someData = 20
    override fun superClassfunc(){
    println("fun sub class printing: $someData")
    }
    }
    fun main(){
    val obj = Sub()
    obj.superClassfunc()
    }
  • 받드시 open 키워드로 선언 해야지 상속이 가능하다!
  • 만약 오버라이딩 한다면 overide를 사용해야한다

접근 제한자

  • 접근 제한자(visibility modifier)란 클래스 멤버를 외부의 어느 범위 까지 이용하게 할 것인지를 결정
    접근 제한자 최상위에서 이용 클래스 멤버에서 이용
    public 모든 파일에서 가능 모든 클래스에서 가능
    internal 같은 모듈 내에서 가능 같은 모듈 내에서 가능
    protected 사용 불가 상속 관계의 하위 클래스에서만 가능
    private 파일 내부에서만 이용 클래스 내부에서만 이용

04-03 코틀린의 클래스 종류
데이터 클래스

  • 데이터 클래스는 data 키워드로 선언하면 자주 사용하는 데이터를 객체로 묶어줌
    ▪ 데이터 클래스는 VO(value-object) 클래스를 편리하게 이용할 수 있게 해줌
  • 예시) (데이터 클래스 선언 및 사용 예시)
    class NonDataClass(val name: String, val email: String, val age: Int)
    data class DataClass(val name: String, val email: String, val age: Int)

fun main(){
val data1 = DataClass("stef","a@hotmail.com",10)
val data2 = DataClass("stef","a@hotmail.com",10)

  • 왜 사용하는지….
    예시)
    class NonDataClass(val name: String, val email: String, val age: Int)
    data class DataClass(val name: String, val email: String, val age: Int)

fun main(){
//comparing normal class with data class
val nonData1 = NonDataClass("stef","a@hotmail.com",10)
val nonData2 = NonDataClass("stef","a@hotmail.com",10)

val data1 = DataClass("stef","a@hotmail.com",10)
val data2 = DataClass("stef","a@hotmail.com",10)

println("non data class equals: ${nonData1.equals(nonData2)}")
println("data class equals: ${data1.equals(data2)}")

=>
non data class equals: false
data class equals: true

  • 참고로 'equals()' 함수로 일반 클래스의 객체를 비교하면 false 이지만 데이터 클래스이 객체를 비교해서 true 이다.
    ▪ => 주 생성자의 멤버 변수가 같은지만 판단한다

오브젝트 클래스(=>anonymous class)

  • 자바의 익명 클래스와 비슷하다
  • 자신의 이름이 없어서 조상의 이름을 사용한다
  • 이 클래스는 클래스와 다르게 이름이 없다
    ▪ 선언하면서 동시에 객체를 생성해야한다
  • 코틀리에서는 이렇게 생성한다….
    val obj = object {
    var data = 10
    fun some(){
    println("data: $data")
    }
    }
  • 만약 위에 있는 예시의 obj 객체로 클래스에 선언한 멤버에 접근하면 오류가 난다.
    ▪ 이유:
    ○ `object로 선언 했지만 타입을 명시 안함
    ○ 이 객체는 코틀린의 최상위 타입인 Any 로 취급하는데.. 만약 data나 some() 접근하면 해당 멤버가 없어소 오류
  • 그래서 보통 object 뒤에 클래스의 생위 또는 인터페이스를 입력
  • 예시)
    //object 클래스 알아보기....
    //obj 클래스를 위한 상위 클래스
    open class ClassForObj {
    open var data = 30
    open fun some(){
    println("super data: $data")
    }
    }

val obj = object: ClassForObj() {//상위 클래스 상속
override var data = 10 //오버라이드
override fun some(){ //오버라이드
println("obj data: $data")
}
}

fun main(){
//printing object class
obj.data = 30 //성공
obj.some() //성공
}

컴패니언 클래스

  • 컴패니언 클래스는 멤버 변수나 함수를 클래스 이름으로 접근하고자 할 때 사용
  • 예시1)
    class MyClass{
    var data = 10
    fun some(){
    println(data)
    }
    }
    fun main(){
    val obj = MyClass()
    obj.data =20 //성공
    obj.some() //성공
    MyClass.data =20 //오류
    MyClass.some() //오류

}

  • 하지만 companion 선언해서 클래스 이름으로 멤버에 접근할 수 있다!
    //Companion class 예시..
    class MyClass{
    companion object{
    var data = 10
    fun some(){
    println(data)
    }
    }
    }

fun main(){
val obj = MyClass()
//obj.data = 20 //오류
//obj.some() //오류
MyClass.data =20 //성공
MyClass.some() //성공
}

  • 클래스 내부에 companion object { } 형태로 선언하면 클래스 이름으로 접근 가능!!!
profile
pro한 프로그래머가 되자!

0개의 댓글