简体   繁体   English

如何从不同的罐子加载相同的类

[英]how to load same class from different jars

I have a class Client.java in two different jars jar1 & jar2 Now at run time i want to decide which Client.class loaded like 我在两个不同的jar jar1和jar2中有一个类Client.java现在在运行时我想决定加载哪个Client.class

if (country==india){
         // load Client class of jar1
) else{
        load client class from jar2 
}

can i do that... 我能做到吗......

If the 2 classes have the same package name, ie com.mycompany.Client, then you end up in a situation where it is somewhat arbitrary which version of Client is loaded. 如果这两个类具有相同的包名,即com.mycompany.Client,那么最终会导致加载哪个版本的Client有些随意。 It comes down to which is on the classpath first. 它归结为首先在类路径上。 This is a JAR hell situation http://en.wikipedia.org/wiki/Java_Classloader#JAR_hell . 这是一个JAR地狱的情况http://en.wikipedia.org/wiki/Java_Classloader#JAR_hell

This is a good situation to avoid but if you absolutely must have different versions of the same class, there are ways to do it. 这是一个要避免的好情况,但是如果你必须拥有同一个类的不同版本,那么有办法做到这一点。 One way is to use a custom classloader and the classloader will know which version you need to do. 一种方法是使用自定义类加载器,类加载器将知道您需要执行哪个版本。 This is not a trivial thing to do and can be difficult to manage. 这不是一件容易的事情,而且难以管理。 The OSGi framework is an alternative to help manage this (it uses custom classloaders under the hood), but I wouldn't use that if you just have one instance of a class as it is another framework that takes time and maintenance. OSGi框架是帮助管理它的另一种选择(它使用自定义类加载器),但如果你只有一个类的实例,我不会使用它,因为它是另一个需要时间和维护的框架。

Bottom line: avoid the situation if you can and take the path of least resistance if you cannot. 底线:如果可以的话,避免这种情况,如果不能,就采取阻力最小的路径。

If the classes do have different package names, @Casidiablo has provided a good answer. 如果类有不同的包名,@ Casidiablo提供了一个很好的答案。

You will have to use the "complete" name of the path. 您必须使用路径的“完整”名称。 For example: 例如:

if (country==india){
         name.first.package.Client client = new name.first.package.Client();
} else{
         name.second.package.Client client = new name.second.package.Client();
}

Anyway... I'd try to avoid doing things like that... that make your code difficult to read and mantain. 无论如何......我会尽量避免做那样的事情......这会使你的代码难以阅读和维护。

If you really have two copies a class, with exactly the same fully-qualified name, in two jars, then ... 如果你真的有两个副本,一个具有完全相同的完全限定名称的类,在两个罐子里,那么......

If you want to be safe, you should not put either of them in the classpath of your default class loader. 如果您想要安全,则不应将它们中的任何一个放在默认类加载器的类路径中。 You will need to create two additional class loaders, and put one of the jars in each. 您将需要创建另外两个类加载器,并在每个加载器中放入一个jar。 You will need to obtain a Class for the two classes, and you will need to use reflection to create the instance of the one you want.. 您将需要为这两个类获取一个类,并且您将需要使用反射来创建所需的实例。

I think you have 2 ways: 我认为你有两种方式:

1) Define an Interface Client, and implements diferent classes, for example: IndiaClient and Country2Client; 1)定义一个接口客户端,并实现不同的类,例如:IndiaClient和Country2Client; Then 然后

interface Client {...}
    class IndiaClient implements Client {...}
    class Country2Client implements Client {...}

    Client client;
    if (country==india){
        client = new IndiaClient();
    ) else{
        client = new Country2Client();
    }

2) Keep your way with the same class name in 2 different jar files, but you still need a interface or super class, and to use different ClassLoaders to load your Client classes: 2)在2个不同的jar文件中使用相同的类名继续使用,但是仍然需要一个接口或超类,并使用不同的ClassLoader来加载Client类:

interface IClient {...}
    class Client implements IClient {...} // in jar1
    class Client implements IClient {...} // in jar2

    Class<IClient> clientClass;
    if (country==india){
        clientClass = classLoader1.loadClass("package.Client");
    ) else{
        clientClass = classLoader2.loadClass("package.Client");
    }
    IClient client = clientClass.newInstance();
  • As for how to get the classLoaders, you can refer to JDK documents. 至于如何获取classLoaders,可以参考JDK文档。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

相关问题 如何从类路径中的不同jar加载一个相同的命名资源? - How to load one of same named resources from different jars in a classpath? 如何将 jars 从不同位置动态加载到当前类加载器中? - How to load jars dynamically from different locations into current class loader? 从不同的罐子装载相同的类 - Loading same class from different jars 如何从java maven项目中的两个不同版本的jar加载类的两个版本? - How to load two versions of a class from two different versions of jars in a java maven project? 如何为每个jar从相同的源但不同的主类创建多个jar? - How can I create multiple jars from the same source but different main class for each jar? 如何区分从不同目录启动的相同jar? - How to distinguish same jars started from different directories? 如何从不同的JAR中读取多个具有相同名称的资源文件? - How to read several resource files with the same name from different JARs? 从不同的JAR调用相同的方法 - Calling same Method From Different JARs 如果不同的 jars 在插件 Z68995FCBF432492D15484D04A9D2AC4 中具有相同的 class 名称,则访问 class - Accessing class if different jars having same class name in plugin jar 如何使用两个不同的类加载器加载同一类 - How to load same class with two different classloaders
 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM