因此,我有点理解Java ClassLoader is的含义,因为它为JVM准备了已编译的.class文件。我只是勉强了解how it works,因为它试图通过一系列递归调用父类ClassLoader的步骤来加载类。我无法理解的是如何确定ClassLoader。也就是说,如何为类选择ClassLoader?

我现在要问这个问题,因为我基本上遇到了以下问题:I can't cast a child class to the implemented interface

该类如下所示:

public class AccountBoImpl implements AccountBo {
...
}

这是我的(略作编辑的)stacktrace的结尾:
15:49:47.269 [DefaultThreadPool-7] ERROR com.company.app.kem.biz.ao -
java.lang.ClassCastException: com.company.app.department.bo.AccountBoImpl cannot be cast to com.company.domain.core.biz.AccountBo
    at com.company.domain.core.biz.AccountBOF.findBySomething(AccountBOF.java:62) ~[Client-1.0.0-SNAPSHOT.jar:na]
    at com.company.domain.shared.biz.applogic.balances.SiteAccountBalanceProcessor.setUnbilledUsage(SiteAccountBalanceProcessor.java:347) ~[Domain-1.0.0-SNAPSHOT.jar:na]

在这里,AccountBoImpl和AccountBo(AccountBoImpl实现的接口)之间的包是不同的。我想知道是什么决定了如何加载这些类。例如,为什么在导入com.company.app.billing.bo.AccountBo;时将com.company.domain.core.biz软件包加载到AccountBo?我知道这段代码中的某个时刻,会调用一个Module类,该类可能会初始化这些类。但是我不确定在此Module类中要寻找什么。

最后,要弄清楚为什么该类被错误地加载,我假设我需要找出它的加载位置/时间。但是我该怎么做呢?我只知道类是按需加载的(无论这实际上意味着什么),但是我不知道如何解决这个问题。例如,使用变量,我可以调试/进入代码以查看何时分配了变量值。但是上课...?我在找什么?我知道在此代码库中,我们有旧代码,这些旧代码提供了与新代码相同的许多类,但是如何使用此信息解决我的问题?

如果我遗漏了重要信息或这个问题似乎很含糊,我事先表示歉意。我不知道如何解决这个问题,因为我昨天才知道ClassLoaders存在。

最佳答案

如何解析简单名称AccountBo的决定是在编译时做出的。

如果您的类中确实有一个import com.company.app.billing.bo.AccountBo;语句,则不可能将implements AccountBo子句解析为其他包的类。
ClassCastException正是在承认这一点,因为它说您的 class 是而不是可分配给com.company.domain.core.biz.AccountBo

因此,类加载器没有问题,标识符解析错误也没有问题。您的类实现了com.company.app.billing.bo.AccountBo,但是在findBySomething类的com.company.domain.core.biz.AccountBOF方法中,是尝试将您的类的实例强制转换为未实现的com.company.domain.core.biz.AccountBo

通常,使用带有此类易于混淆名称的公共类不是一个好主意。

关于java - 如何加载Java类,如何确定在何处/何时/为什么加载类?,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/57916027/

10-09 05:34