Reputation: 329
I have an inline function with a reified type parameter taking a lambda, which returns a new instance of an anonymous class which has a single method taking that reified type parameter and passing it to the lambda.
inline fun <reified T : Any> eventHandler(crossinline handler: (T) -> Unit) = object {
@Handler
fun event(event: T) = handler(event)
}
It is used like eventHandler<ExampleEvent> { println(it.data); }
and everything compiles.
However investigating the generated bytecode of the class created on the mentioned call, I get this for the event method:
public final void event(example.ExampleEvent);
descriptor: (Ljava/lang/Object;)V
[...]
Signature: #53 // (Lexample.ExampleEvent;)V
So while it correctly remembers the type in the Signature, it discards it in the descriptor; therefore thatEventMethod.getParameterTypes()
will have Object
instead of ExampleEvent
.
Is this a bug or intended behavior? Furthermore, if this is intended, could there be some other way of realizing my goal (which is to prevent having to create that clumsy object everywhere, add a dummy method with @Handler etc.)?
Upvotes: 4
Views: 727
Reputation: 2931
So if I understand correctly your question is: is it ok that functions with reified generics in bytecode look like functions with erased types.
Answer is "yes". That's why functions with reified generics can bi inline-only. Their body is being full inlined into caller. And of course types are not erased there (at cost of bloating caller function bytecode size).
Upvotes: 1