¿Cómo prohibir las llamadas a funciones con un cierto subtipo de un tipo de parámetro?

Supongamos que tengo una function genérica:

fun <T: Foo> bar(t: T) { ... } 

Luego, más tarde en algún momento, decidí que no tiene sentido (o incluso es erróneo) llamar a la bar(...) con T especializada como Qux , que es, por supuesto, uno de los subtypes de Foo . Pero tengo una fuerte razón para no cambiar la jerarquía de classs (por ejemplo, no tengo acceso a ese código).

¿Hay alguna forma de prohibir las llamadas a bar(t) con T especializado como Qux ?

Hay una forma de prohibir las llamadas para un cierto argumento de tipo genérico: la desaprobación. Usar la anotación @Deprecated en este caso parece bastante torpe, pero resuelve el problema (*).

Puede definir una sobrecarga de bar(...) con un tipo más concreto y descartar la sobrecarga con nivel DeprecationLevel.ERROR :

 @Deprecated("bar should not be called with Qux", level = DeprecationLevel.ERROR) fun <T : Qux> bar(t: T) = bar(t as Foo) 

Después de eso, cuando se resuelve una llamada de bar(...) para un argumento Qux , la sobrecarga obsoleta tendrá prioridad porque presenta más types concretos. Por lo tanto, las llamadas producirán un error en time de compilation:

 bar(Qux()) ^ Using 'bar(T): Unit' is an error. bar should not be called with Qux 

(*) Tenga en count, sin embargo, que esto solo funcionará para Qux como tipo estático (el usado para la resolución de la llamada), y la function todavía se puede llamar como bar(Qux() as Foo) . Muy esperado, no puede producir un error en time de compilation si el tipo de argumento solo se conoce en time de ejecución.


El mismo enfoque puede usarse para producir errores o advertencias para funciones que solo deberían reactjsr en null s de alguna manera, por lo que llamarlas con un tipo no nulo no tiene sentido:

 fun checkNotNull(x: Any?) = x ?: throw IllegalStateException("Should not be null") @Deprecated("It is meaningless with a not-null argument.", DeprecationLevel.WARNING) @JvmName("checkNotNull--notNullArgument") fun checkNotNull(x: Any) = checkNotNull(x as Any?) 
  • Inferencia de tipo Observable.combineLatest en kotlin
  • Clase Derivada Parcelable en Kotlin
  • Error al ejecutar un servlet de Apache Tomcat escrito en Kotlin
  • Problemas al analizar datos con RxJava + Kotlin
  • Kotlin enum class en el performance de Android
  • ¿Por qué no está vacío en las collections de Kotlin una propiedad?
  • En Android Studio, ¿cómo cambio las convenciones de nombres de Kotlin?
  • Fragmento Button onClickListener no se está ejecutando
  • Kotlin: los generics reificados no parecen funcionar bien para comparaciones hash / iguales
  • Ejecute testings junit escritas en Kotlin con la anotación @category
  • Kotlin: hacer visible una function interna para testings unitarias