Reified di Kotlin — apa itu, sintaksis dan penerapan

Penulis: IT Sectr Diterbitkan: 2026-06-21 Waktu membaca: 8 mnt

reified — kata kunci dalam bahasa Kotlin yang memungkinkan akses ke tipe parameter generic di dalam inline-function pada saat eksekusi. Dalam generic biasa, type erasure bekerja — informasi tentang tipe dihapus pada tahap kompilasi, tetapi reified menyimpannya. Menurut Kotlin Documentation, 2025, reified hanya bekerja di dalam inline-function, karena kompiler mensubstitusi tipe nyata pada tahap inlining.

Poin utama

  • reified — pengubah parameter generic yang menyimpan informasi tentang tipe di runtime
  • Inline only — reified bekerja secara eksklusif di dalam inline-function
  • Type erasure — mekanisme standar Java/Kotlin yang menghapus tipe generic; reified menghindarinya
  • Pemeriksaan is — dimungkinkan: if (value is T) alih-alih if (value is String)
  • Pembuatan instance — membuat T::class.java.newInstance() tanpa mengirimkan Class

Apa itu reified di Kotlin?

reified — adalah pengubah parameter generic dari fungsi inline yang membuat tipe menjadi nyata (reify — “menjadikan nyata”) di runtime. Tanpa reified, tipe T di dalam fungsi generic tidak dapat diakses — kompiler menerapkan type erasure, menghapus semua informasi tentang tipe. reified memaksa kompiler untuk mensubstitusi tipe konkret di tempat pemanggilan, membuatnya dapat diakses melalui T::class dan operator is.

Menurut Kotlin Survey by Kodee (2024), reified type parameters termasuk dalam sepuluh fitur Kotlin yang paling banyak diminati — 52% pengembang yang disurvei menggunakannya, terutama untuk menulis pabrik generic, container DI, dan serializer. Reified sangat populer dalam kombinasi dengan Gson, Moshi, dan Kotlinx Serialization.

Secara teknis, mekanismenya sederhana: saat memanggil fungsi inline dengan parameter reified, kompiler mengetahui tipe konkret argumen (Int, String, User) dan mensubstitusikannya ke tempat T. Dalam bytecode, parameter reified berubah menjadi Class biasa, dikirimkan sebagai argumen tersembunyi.

Gunakan reified untuk menulis fungsi generic di mana tipe diperlukan di runtime — pembuatan instance, pemeriksaan tipe, mendapatkan Class untuk refleksi atau serialisasi.

Masalah type erasure di generic

Type erasure — mekanisme Java dan Kotlin di mana informasi tentang parameter generic dihapus selama kompilasi. Dalam bytecode, List dan List menjadi hanya List. Ini dilakukan untuk kompatibilitas mundur dengan Java 1.4, di mana generic tidak ada, tetapi menciptakan keterbatasan saat bekerja dengan tipe di runtime.

kotlin
// ❌ Galat: Tidak dapat memeriksa instance dari tipe yang dihapus
fun <T> checkType(value: Any) {
    if (value is T) { // type erasure — T tidak diketahui
        println("Tipe cocok")
    }
}

// ✅ Solution: pass Class as parameter
fun <T> checkTypeWithClass(
    value: Any,
    clazz: Class<T>
) {
    if (clazz.isInstance(value)) {
        println("Tipe cocok")
    }
}

Dalam contoh, checkType tidak dapat dikompilasi karena type erasure — kompiler tidak tahu tipe apa yang harus disubstitusi ke tempat T. Di checkTypeWithClass masalah diselesaikan dengan mengirimkan Class secara eksplisit, tetapi ini memerlukan boilerplate: setiap pemanggilan disertai dengan .java atau ::class.java. reified sepenuhnya menghilangkan boilerplate ini.

Sintaksis reified dan mekanisme kerja

Pengubah reified ditempatkan sebelum parameter generic dalam fungsi inline. Fungsi harus inline — kompiler harus memiliki kemampuan untuk mensubstitusi tipe konkret pada tahap inlining.

kotlin
inline fun <reified T> isA(value: Any): Boolean {
    return value is T
}

fun main() {
    println(isA<String>("Halo")) // true
    println(isA<Int>("Halo"))  // false
}

Selama kompilasi, pemanggilan isA("Hello") diganti dengan pemeriksaan value is String. Pemanggilan isA("Hello") — dengan value is Int. Tipe disubstitusi secara harfiah, yang memungkinkan penggunaan is, as, ::class, dan operasi lain yang tidak tersedia pada type erasure.

Dekompilasi fungsi reified

Jika kita mendekompilasi bytecode isA("Hello"), IntelliJ IDEA akan menampilkan kira-kira hasil berikut di Java: String.class.isInstance(value). Alih-alih parameter generic, kompiler telah mensubstitusi java.lang.String.class konkret — tidak ada refleksi dengan pencarian tipe berdasarkan nama, hanya referensi langsung ke kelas.

Pemeriksaan tipe dengan reified: is dan as

Penerapan reified yang paling umum — pemeriksaan tipe melalui operator is. Dalam fungsi generic biasa, value is T tidak dapat dikompilasi. Dengan reified, ini bekerja seperti dengan kelas biasa: value is String, value is List (hampir — dengan mempertimbangkan keterbatasan reified untuk tipe yang diparametrisasi).

kotlin
inline fun <reified T> List<Any>.filterByType(): List<T> {
    return this.filter { it is T }.map { it as T }
}

val mixed = listOf("a", 1, "b", 2)
val strings = mixed.filterByType<String>() // ["a", "b"]
val ints = mixed.filterByType<Int>()    // [1, 2]

Fungsi ekstensi filterByType memfilter daftar, hanya menyisakan elemen dari tipe yang ditentukan. Tanpa reified, harus menulis filterByType(list) dengan parameter Class. Dengan reified, pemanggilan terbaca sebagai operasi alami pada daftar, yang meningkatkan keterbacaan rantai pemrosesan data.

Menurut data Kotlin Coroutines Guide (JetBrains, 2025), pemeriksaan tipe reified digunakan di launch dan async untuk mengirimkan tipe hasil coroutine, yang memungkinkan menghindari penentuan tipe secara eksplisit di sebagian besar kasus.

Refleksi dengan reified: pembuatan instance dan akses ke Class

reified memberikan akses ke T::class — referensi ke KClass, dari mana Java Class dapat diperoleh melalui .java. Ini membuka kemungkinan untuk pembuatan instance melalui refleksi, bekerja dengan serializer, dan mendapatkan anotasi kelas selama eksekusi.

kotlin
inline fun <reified T> createInstance(): T =
    T::class.java.getDeclaredConstructor().newInstance()

// Penggunaan
data class User(val name: String = "default")
val user = createInstance<User>()

// Serialisasi dengan Gson
inline fun <reified T> Gson.fromJson(json: String): T =
    this.fromJson(json, T::class.java)

// Mendapatkan anotasi
inline fun <reified T> hasAnnotation<A>(): Boolean where A : Annotation =
    T::class.java.isAnnotationPresent(A::class.java)

Wrapper fromJson untuk Gson — contoh klasik penggunaan reified di produksi. Alih-alih gson.fromJson(json, User::class.java) dapat menulis gson.fromJson(json). Ini tampak seperti peningkatan kecil, tetapi dalam proyek dengan ratusan pemanggilan serialisasi, reified secara signifikan mengurangi boilerplate dan membuat kode lebih bersih.

Keterbatasan reified dan alternatif

reified memiliki keterbatasan. Pertama — hanya bekerja di dalam fungsi inline. Jika fungsi tidak dapat dibuat inline (misalnya rekursif atau terlalu besar), reified tidak tersedia. Kedua — reified tidak dapat digunakan langsung dengan fungsi suspend, hanya melalui wrapper inline.

Ketiga — reified tidak bekerja sepenuhnya dengan tipe yang diparametrisasi. Misalnya, filterByType>() dapat memberikan hasil yang tidak terduga, karena untuk tipe yang diparametrisasi, reified hanya menyimpan tipe mentah (List), tanpa menentukan argumen generic. Untuk pemeriksaan lengkap tipe yang diparametrisasi, diperlukan refleksi dengan TypeToken.

OperasiDengan reifiedTanpa reified
value is T✅ Berfungsi❌ Galat kompilasi
T::class✅ Berfungsi❌ Galat kompilasi
List is T⚠️ Hanya raw type❌ Galat
Pembuatan instance✅ Melalui refleksi❌ Perlu Class
Fungsi Suspend❌ Hanya melalui wrapper inline❌ Tidak berlaku

Untuk kasus di mana reified tidak tersedia, gunakan pola dengan pengiriman eksplisit Class atau TypeToken dari pustaka (misalnya, Gson TypeToken atau Jackson TypeReference). Pendekatan ini berfungsi di fungsi apa pun, tetapi memerlukan boilerplate dan kurang nyaman.

Pertanyaan yang sering diajukan

Mengapa reified hanya bekerja dengan fungsi inline?

Kompiler mengganti parameter reified T dengan tipe konkret selama inlining body fungsi. Jika fungsi tidak inline, kompiler tidak memiliki tempat untuk mensubstitusi tipe — pemanggilan fungsi generic terjadi melalui bytecode seragam, di mana T telah dihapus. Inline membuat salinan bytecode terpisah untuk setiap tipe-argumen.

Bisakah mendeklarasikan reified property?

Tidak, reified hanya berlaku untuk parameter fungsi. Untuk properti, gunakan pola inline fun dengan nilai kembali atau pengiriman eksplisit Class melalui konstruktor. Extension properties juga tidak mendukung reified.

Bagaimana reified bekerja dengan tipe nullable?

reified mendukung tipe nullable: reified T : Any (non-null) dan sederhana reified T (dapat nullable). Untuk tipe nullable, T::class mengembalikan kelas untuk versi non-null (String::class untuk String?). Pemeriksaan value is T memperhitungkan null: jika T = String?, maka null is T = true.

Apakah reified memiliki overhead?

Minimal. reified tidak menggunakan refleksi — kompiler mensubstitusi tipe konkret pada tahap inlining. Dalam bytecode, ini adalah referensi langsung ke kelas (ldc + checkcast/invokevirtual). Tidak ada overhead dibandingkan dengan pengiriman manual Class — kedua varian menghasilkan bytecode yang sama.

Bisakah reified digunakan dalam pengembangan Android?

Ya, reified digunakan secara aktif di Android. Bundle.getParcelable(), Intent.getSerializableExtra(), viewModels() dari Android KTX — semua fungsi ini menggunakan reified untuk menghindari pengiriman eksplisit Class. Menurut data Google Android Docs (2025), reified direkomendasikan untuk API generic di mana tipe diperlukan di runtime.

Ringkasan

  • reified — pengubah parameter generic fungsi inline, menyimpan tipe di runtime
  • Type erasure — mekanisme standar penghapusan tipe; reified menghindarinya melalui inlining
  • is/as — pemeriksaan dan konversi tipe bekerja dengan reified seperti dengan kelas biasa
  • Referensi kelas — T::class dan T::class.java tersedia untuk refleksi dan serialisasi
  • Hanya inline — reified tidak mungkin tanpa fungsi inline karena mekanisme substitusi tipe
  • Tipe diparametrisasi — reified tidak menyimpan argumen generic (hanya raw type)
  • Penerapan — serialisasi Gson/Moshi, container DI, pemeriksaan tipe di koleksi, Android KTX

Kami akan mengembangkan aplikasi seluler turnkey

IT Sectr membuat aplikasi iOS dan Android untuk startup dan bisnis sejak 2017. Kami akan memberi saran dan mengusulkan solusi terbaik.

Diskusikan proyek

Baca juga