inflearn logo
강의

강의

N
챌린지

챌린지

멘토링

멘토링

N
클립

클립

로드맵

로드맵

지식공유

코틀린 고급편

23강. 리플렉션 활용 - 타입 안전 이종 컨테이너와 슈퍼 타입 토큰

23강 타입 안전 이종 컨테이너 예제 관련 문의 드립니다.

110

teddy

작성한 질문수 3

0

저같은 경우, 7:32 부분에서 List<GoldFish> 를 저장했다가 List<Carp> 타입을 꺼내려고 하면

"class generic.GoldFish cannot be cast to class generic.Carp (generic.GoldFish and generic.Carp are in unnamed module of loader 'app')" 와 같은 오류가 발생하는데,

정상적으로 금붕어 리스트가 반환되는게 맞는지요 ? 제가 뭔가 놓친 부분이 있을까 궁금하여 문의 드립니다.

샘플코드는 다음과 같습니다.

package reflection

import generic.Carp
import generic.GoldFish
import kotlin.reflect.KClass
import kotlin.reflect.full.cast

class TypeSafeCage {
    val animals: MutableMap<KClass<*>, Any> = mutableMapOf()

    inline fun <reified T : Any> getOne(): T {
        return T::class.cast(animals[T::class])
    }

    inline fun <reified T : Any> putOne(animal: T) {
        animals[T::class] = T::class.cast(animal)
    }
}

fun main() {
    val cage = TypeSafeCage()
    cage.putOne(listOf(GoldFish("금붕어1"), GoldFish("금붕어2")))
    cage.getOne<List<Carp>>().forEach { println(it::class.simpleName) }
}


// 다른 패키지 파일
package generic

open class Animal(
    val name: String
)

open class Fish(name: String) : Animal(name)

class GoldFish(name: String) : Fish(name)

class Carp(name: String) : Fish(name)

 

강의 중 영상 캡쳐 화면

Cursor_및_코틀린_고급편___학습_페이지.png

 

kotlin 함수형-프로그래밍 객체지향

답변 2

0

최태현

안녕하세요! Teddy님~ 🙂 질문 주셔서 감사합니다!!

"class generic.GoldFish cannot be cast to class generic.Carp (generic.GoldFish and generic.Carp are in unnamed module of loader 'app')" 와 같은 오류가 발생하는데,

정상적으로 금붕어 리스트가 반환되는게 맞는지요 ? 제가 뭔가 놓친 부분이 있을까 궁금하여 문의 드립니다.

로 문의 주신 내용이 핵심 같은데요..! 금붕어가 들어 있는데 List<Carp> 로 타입을 받기 때문에 금붕어가 반환 되려다가 에러가 나오게 됩니다!

 

즉, 정상적으로 라는 단어가

  • putOne으로 금붕어를 넣었으니 꺼낼 때도 금붕어다

라는 관점에서 맞기도 하고요

  • 금붕어를 꺼냈으나 잉어로 형변환을 하려고 해 오류가 발생했다

라는 관점에서는 아니기도 할 것 같습니다.

 

감사합니다. 🙇

0

인프런 AI 인턴

안녕하세요, 인프런 AI 인턴입니다. 성태혁님, 코틀린 강의에서 발생한 문제에 대해 문의 주셔서 감사합니다.

질문 내용을 확인해보니, “금붕어 리스트가 반환되어야 하는데 잉어 리스트로 가져오려 할 때 발생하는 오류”에 대한 부분을 설명 드리겠습니다. TypeSafeCage의 구조상, 저장된 객체와 꺼내려는 객체의 타입이 일치하지 않으면 해당 오류가 발생하는 게 정상입니다.

즉, 안전한 타입 이종 컨테이너를 사용하여 데이터 타입을 제어하려고 하지만, 컨테이너에서 다른 타입으로 데이터를 꺼내려고 할 때 변환이 불가능한 상황입니다.

주요원인:
- putOne 메서드를 통해 GoldFish 리스트를 저장한 후, getOne을 통해 Carp 타입으로 리스트를 꺼내려고 시도하기 때문에 타입 불일치가 발생합니다. KClass<*>를 키로 사용할 때, 실제로 저장된 타입을 명확하게 지정할 필요가 있습니다.

강의 캡처 화면에 나와 있듯이, List<Carp>에는 금붕어가 저장되어 있다는 점을 보여주며, 이 컨텍스트에서는 코틀린이 타입 안전성을 보장하지 않는 상황을 주의해야 한다는 교육적 목적을 염두에 두신 것 같습니다.

이러한 타입 불일치 문제는 타입 캐스팅을 신중히 활용하여 해결할 수 있습니다. 만약 구조적으로 다양한 타입의 데이터가 저장되어야 하는 상황이라면, 다른 방법을 고려해야 합니다. 예를 들어, 저장과 가져오는 로직을 명확하게 타입별로 분리해서 관리하거나, 범용적으로 처리할 수 있는 인터페이스를 도입하는 방식 등을요.

저는 질문자님의 이해를 돕고자 지식공유자님의 기존 답변을 참고하여 유사한 답변 링크를 추천해드리고 있습니다. 현재 베타 기능으로 답변이 만족스럽지 않을 수 있는 점 양해 부탁드립니다. 🙏 추가적으로 궁금한 점이 있으시면, 이어서 질문해 주세요. 곧 지식공유자께서 답변해 주실 것입니다.

질문있습니다

0

22

1

KType 관련 Kotlin 2.3 변경점

1

61

2

Kotlin 2.0(K2 컴파일러)에서 달라진 Java SAM 변환 동작

2

98

3

SuperTypeSafeCage에 대해 질문드립니다

0

61

2

좋은 코드 예시

0

94

2

val 키워드도 setValue가 있나요?

0

85

2

반공변성 질문드립니다.

1

113

3

[23강] SuperTypeToken의 equals 관련 질문

1

95

2

abstract class Fish(name:String):Animal(name)

0

105

2

지식공유자님 inline에 대해서의 질문과 추가적인 질문 1가지가 있습니다!

1

117

1

안녕하세요 JMH 설정 관련 팁을 드릴까 합니다! (24년 12월 16일 기준)

0

164

2

Generic Func 질문이 있습니다

1

103

1

2강부터 영상 재생이 안되네요ㅠㅠ

0

151

2

by lazy 블럭 안에서 suspend 함수의 결과값을 받는게 가능한가요?

0

389

1

DSL 만들기

0

285

1

Sequence vs Stream

1

250

1

코틀린 indent 코드 스타일 질문입니다.

0

263

1

non-local return 질문입니다.

1

227

1

SynchronizedLazyImpl 함수관련 질문

0

423

2

제네릭 클래스를 정의하는 경우, 반드시 변성을 고려하는 것이 바람직한가요?

4

1325

1

실무에서 lateinit 이 필요한 경우는 어떤 상황일까요?

1

453

1

4강 타입소거 관련 질문

1

330

2

추상클래스의 공변 / 반공변, 추상 제네릭 일급컬랙션 리팩토링 에 대한 질문입니다.

2

598

1

lateinit 키워드 관련해서 질문드립니다!

1

314

1