Kotlin: odpowiednik getClass () dla KClass

94

W Javie możemy rozwiązać klasę zmiennej za pomocą getClass()like something.getClass(). W Kotlinie zdaję sobie sprawę, something.javaClassco jest fajne, ale chcę mieć KClassto samo. Widziałem Something::classskładnię, ale to nie jest to, czego potrzebuję. Potrzebuję KClass zmiennej. Czy taka funkcjonalność istnieje?

Jire
źródło

Odpowiedzi:

144

Najłatwiejszym sposobem na osiągnięcie tego od Kotlin 1.1 jest składnia odwołania do klasy :

something::class

Jeśli używasz Kotlin 1.0, możesz przekonwertować uzyskaną klasę Java na instancję KClass, wywołując .kotlinwłaściwość rozszerzenia:

something.javaClass.kotlin
Alexander Udalov
źródło
Gdziekolwiek mogę śledzić wykonanie czegoś :: class?
Nishad
1
@Nishad Najłatwiejszym miejscem byłoby przyjrzenie się wygenerowanemu kodowi bajtowemu (np. Z javap)
Alexander Udalov
2
Możesz również użyć, KClass::classaby pobrać bieżący obiekt klasy.
Saminda Peramuna
1
Należy zwrócić uwagę na to, że something::classpowraca, KClass<out Something>gdy something.javaClass.kotlinzwracaKClass<Something>
KylePlusPlus
1
@SamindaPeramuna To jest po prostu błędne, KClass :: class zwraca obiekt klasy kotlin.reflect.KClass, a nie bieżący obiekt klasy! Aby to uzyskać, musisz użyć this :: class.
Markus Kreusch
11

EDYCJA: Zobacz komentarze poniżej i odpowiedź Aleksandra powyżej. Ta rada była pierwotnie dla Kotlin 1.0 i wydaje się, że jest już nieaktualna.

Ponieważ język nie obsługuje jeszcze bezpośredniego sposobu uzyskania tego, rozważ na razie zdefiniowanie metody rozszerzenia .

fun<T: Any> T.getClass(): KClass<T> {
    return javaClass.kotlin
}

val test = 0
println("Kotlin type: ${test.getClass()}")

Lub, jeśli wolisz nieruchomość:

val<T: Any> T.kClass: KClass<T>
    get() = javaClass.kotlin

val test = 0
println("Kotlin type: ${test.kClass}")
dherman
źródło
1
Możesz pominąć javakawałek i iść prosto Kotlin:fun<T: Any> T.getClass(): KClass<out T> = this::class
TWiStErRob
1
Ta odpowiedź powinna zostać zaktualizowana, aby odzwierciedlić zmiany w 1.1. Teraz można uzyskać zajęcia za pomocąsomeClass::class
Max
2

Oto moje rozwiązanie

val TAG = javaClass.simpleName

Dzięki javaClass.simpleName możesz uzyskać nazwę swojej klasy. Powyższy przykład jest również bardzo przydatny dla programistów Androida, aby zadeklarować na szczycie klasy jako zmienną instancji do celów logowania.

Kashif Anwaar
źródło
1

Oto różne implementacje do pobierania nazw klas. Możesz go wykorzystać zgodnie ze swoimi wymaganiami.

import kotlin.reflect.KClass

val <T : Any > T.kClassName: KClass<out T>
get() {
    return javaClass.kotlin
}

Tutaj możemy uzyskać nazwę klasy w kotlin

val <T : Any > T.classNameKotlin: String?
get() {
    return javaClass.kotlin.simpleName
}

Tutaj możemy uzyskać nazwę klasy w kotlin

val <T : Any > T.classNameJava: String
get() {
    return javaClass.simpleName
}

Oto wyniki następujących operacji.

fun main(){

val userAge = 0

println(userAge.kClassName) 
Output: class java.lang.Integer (Kotlin reflection is not available)

println(userAge.classNameKotlin)
Output: Int

println(userAge.classNameJava)
Output: Integer
}
Muhammad Maqsood
źródło