【问题标题】:Can I get an instance of a class in Java during runtime if I know its ClassLoader (ClassLoader Namespace)如果我知道它的 ClassLoader(ClassLoader 命名空间),我可以在运行时获取 Java 中的类的实例吗
【发布时间】:2014-02-25 20:54:13
【问题描述】:

我只是想知道如果我知道它的类加载器,我是否可以在 JVM 运行时获取一个类的实例(对对象的引用)。请参考下面的代码来理解我的问题。

A类:

package local.run;
public class A {
    public static void main(String[] args) {
        B b = new B();
        b.setCount(5);
        C c = new C();
        c.dummyMethod();
        b.printCount();
    }
}

B类:

package local.run;
public class B {
    public int count = 0;
    public void setCount(int aCount) {
        count = aCount;
    }
    public void printCount() {
        System.out.println(count);
    }
}

C类:

package local.run;    
public class C {
    public void dummyMethod() {
        // Can I get the instance of class B created in class A here? 
        // I don't want to pass the instance of class B as a parameter to this method.
        System.out.println("ClassLoader Namespace -> "+B.class.getProtectionDomain().getCodeSource().getLocation());

        // I know the ClassLoader Namespace of class B
        // How to get instance of class B created in class A???
        System.out.println(b.count); // I wan't to print 5
    }
}

如果这不可行,那么我只是想知道 JSF 如何实现 @ManagedProperty 功能?

【问题讨论】:

    标签: java jsf jvm classloader managed-property


    【解决方案1】:

    不,您无法从 ClassLoader 获取给定类型的实例。 ClassLoader 如何识别您想要的实例?

    你需要一些其他类型的逻辑。和 Peter 一样,我不知道 JSF 到底是怎么做的,所以我举一个 Spring 的例子。

    在提供控制反转容器的 Spring 中,您声明您的 bean。这些由容器管理,即。容器存储它们并控制它们的整个生命周期。如果您在这些 bean 的类之一中有一个字段声明为

    @Value("${someBean.someField}")
    private String copyValueOfThatField;
    

    然后容器负责解析@Value注解中的表达式并将对应的值注入copyValueOfThatField字段。

    在这种情况下,它将使用某个组件遍历容器中注册的所有 bean,找到名为 someBean 的组件,并尝试检索其 someField 属性的值。

    您将在后台进行大量反射以获取对象字段的值。

    JSF 本身就是一个容器,可能会做与上面类似的事情。 Managed 一词的使用应该告诉你这一点。

    【讨论】:

    • 这也是 JSF 实际所做的。查看 JSF Spec 第 5 章、第 3 节和第 4 节了解详细信息。它实际上依赖于 EL 插值(就像 Spring 一样),EL 解析器在其中查找 JSF 容器已在 EL 上下文中注册的 bean 对象。 AFAIK 通过遍历类加载器的可用类列表并扫描每个类的 @ManagedBean(以及 CDI:@Named)注释来找到它们。
    • @mabi 感谢您的澄清。如果需要,您可以提供编辑。
    • 感谢您的回答。
    【解决方案2】:

    要获取实例,您必须在某处拥有一个集合,该集合保留该实例以供查找。我不知道 JSF 具体是如何工作的,但通常你的框架会寻找它识别的特殊注释,并保存用于设置这些字段的实例,或者它有工厂来创建实例。

    【讨论】:

      猜你喜欢
      • 2017-09-30
      • 1970-01-01
      • 2019-08-13
      • 1970-01-01
      • 1970-01-01
      • 2012-04-29
      • 2020-04-23
      • 2010-10-02
      相关资源
      最近更新 更多