【问题标题】:Generics information when using invokedynamic使用 invokedynamic 时的泛型信息
【发布时间】:2016-07-01 15:26:21
【问题描述】:

我正在创建一个 java 框架来在 Invoke dynamic 的帮助下转换 bean。我用 ASM 创建了转换类。为了生成如下所示的转换:

target.setter( convert(source.getter()) );

我用 ASM 编写以下字节码:

mv.visitVarInsn(ALOAD, ARGUMENT_2);
mv.visitVarInsn(ALOAD, ARGUMENT_1);
mv.visitMethodInsn(INVOKEVIRTUAL, sourceClass, sourceGetter.getName(), Type.getMethodDescriptor(sourceGetter), false);
mv.visitInvokeDynamicInsn("convert", Type.getMethodDescriptor(Type.getType(targetSetter.getParameterTypes()[0]), Type.getType(sourceGetter.getReturnType())), converterBootstrapMethod);
mv.visitMethodInsn(INVOKEVIRTUAL, targetClass, targetSetter.getName(), Type.getMethodDescriptor(targetSetter), false);

convert 方法然后搜索可以处理给定类型的转换器。这看起来像:

public static CallSite bootstrap(final MethodHandles.Lookup caller, final String name, final MethodType type) throws Exception {
    final Class<?> sourceType = type.parameterType(0);
    final Class<?> targetType = type.returnType();
    MethodHandle converter = findConverter(sourceType, targetType);
    return new ConstantCallSite( converter.asType(type) );
}

这适用于说字符串到整数的转换。但不适用于泛型。 sourceType 只是Ljava/util/List; 而不是完整的Ljava/util/List&lt;Ljava/lang/String;&gt;;

如何在这个引导方法中获取完整类型?

【问题讨论】:

  • 这是因为type erasure
  • 我知道是什么原因造成的!但是现在如何解决它!

标签: java generics bytecode invokedynamic


【解决方案1】:

如果您可以控制您的 invoke 动态调用站点,则可以向它传递其他参数。在这些参数中,您需要将实际的字段/getter 名称及其声明类传递给调用站点。

在您的引导方法中使用这些信息,您现在可以找到实际的字段/getter,并通过反射 API 提取通用信息。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2011-01-09
    相关资源
    最近更新 更多