当前位置: 首页 > 面试题库 >

Java8动态代理和默认方法

晋承运
2023-03-14
问题内容

拥有具有默认方法的接口的动态代理,如何调用默认方法?通过使用类似的方法,defaultmethod.invoke(this, ...)您可以得到名为的代理调用处理程序(这在某种程度上是正确的,因为您没有为此接口实现的类)。

我有一个使用ASM来创建实现接口的类并将此类调用委派给此类实例的解决方法。但这不是一个好的解决方案,特别是如果默认方法调用其他接口方法(您将获得委托人乒乓球)。JLS对此问题出人意料地保持沉默…

这里是一个小代码示例:

public class Java8Proxy implements InvocationHandler {
    public interface WithDefaultMethod {
        void someMethod();

        default void someDefaultMethod() {
            System.out.println("default method invoked!");
        }
    }

    @Test
    public void invokeTest() {
        WithDefaultMethod proxy = (WithDefaultMethod) Proxy.newProxyInstance(
            WithDefaultMethod.class.getClassLoader(),
            new Class<?>[] { WithDefaultMethod.class }, this);
        proxy.someDefaultMethod();

    }

    @Override
    public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {

        // assuming not knowing the interface before runtime (I wouldn't use a
        // proxy, would I?)
        // what to do here to get the line printed out?

        // This is just a loop
        // method.invoke(this, args);

        return null;
    }
}

问题答案:

您可以在 InvocationHandler中
使用MethodHandles类型。这段代码是从Zero
Turnaround
复制的。
__

Constructor<MethodHandles.Lookup> constructor;
Class<?> declaringClass;
Object result;

if (method.isDefault()) {
   declaringClass = method.getDeclaringClass();
   constructor = MethodHandles.Lookup.class.getDeclaredConstructor(Class.class, int.class);

   constructor.setAccessible(true);

   result = constructor.
      newInstance(declaringClass, MethodHandles.Lookup.PRIVATE).
      unreflectSpecial(method, declaringClass).
      bindTo(proxy).
      invokeWithArguments(args);

   return(result);
}


 类似资料:
  • 主要内容:1 Java8 默认方法的介绍,2 Java8 默认方法的案例1 Java8 默认方法的介绍 Java提供了一种在接口内部创建默认方法的功能。在接口内部定义并带有默认标记的方法称为默认方法。这些方法是非抽象方法。 2 Java8 默认方法的案例 在下面的示例中,Sayable是一个功能接口,其中包含默认值和抽象方法。默认方法的概念用于定义具有默认实现的方法。您还可以覆盖默认方法,以为该方法提供更具体的实现。 输出结果为:  

  • 问题内容: 由于Java 8接口可能具有默认方法。我知道如何从实现方法中显式调用该方法,即(请参阅在Java中显式调用默认方法) 但是,如何在代理服务器上使用反射来 显式 调用默认方法? 例: 编辑: 我知道在我如何反省地调用Java 8默认方法中 提出了类似的问题,但这由于两个原因未能解决我的问题: 在提到的问题,旨在就如何通过反射调用它 一般 -所以默认和覆盖方法没有区别制成-这很简单,你只需

  • 本文向大家介绍Java8默认方法Default Methods原理及实例详解,包括了Java8默认方法Default Methods原理及实例详解的使用技巧和注意事项,需要的朋友参考一下 这篇文章主要介绍了Java8默认方法Default Methods原理及实例详解,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友可以参考下 Java 8 引入了新的语言特性

  • 我有一个类实现了多个具有相同默认方法的接口。我想知道如何从所有接口合成默认方法。例如: 复合模式也相当可观。但是我想用default方法作为mixin来给类不同的行为,而复合模式在这里没有给我静态类型检查。复合模式还引入了额外的内存占用。

  • 本文向大家介绍浅谈Java代理(jdk静态代理、动态代理和cglib动态代理),包括了浅谈Java代理(jdk静态代理、动态代理和cglib动态代理)的使用技巧和注意事项,需要的朋友参考一下 一、代理是Java常用的设计模式,代理类通过调用被代理类的相关方法,并对相关方法进行增强。加入一些非业务性代码,比如事务、日志、报警发邮件等操作。 二、jdk静态代理 1、业务接口 2、业务实现类 3、代理类

  • 通常情况下,Java源代码是向前兼容的。在Java8之前,据我所知,编译的类和源代码都与后来的JDK/JVM版本实现了前向兼容。[更新:这不正确,请参阅下面的注释re'enum'等。]但是,在Java8中添加了缺省方法之后,情况似乎不再是这样了。 例如,我一直使用的库有一个的实现,它包括一个。此方法返回已排序列表内容的副本。这个库作为jar文件依赖项部署,在使用JDK1.8构建的项目中运行良好。