首页
学习
活动
专区
工具
TVP
发布
社区首页 >问答首页 >如何在Java中更改CLASSPATH?

如何在Java中更改CLASSPATH?
EN

Stack Overflow用户
提问于 2008-10-31 08:44:34
回答 6查看 75K关注 0票数 60

如何在Java进程中更改Java进程的CLASSPATH?

在你问我“你为什么要这么做?”我很快就会解释它。

当您运行Clojure REPL时,通常需要在您的CLASSPATH中使用更多的jars来加载Clojure源文件,我希望不必重启Clojure本身(在Emacs上的Slime上使用它时,这并不是一个真正的选择)。

这就是原因,但我不希望这个问题被标记为某种奇怪的语言某种奇怪的编辑器,并被大多数可能有答案的Java开发人员忽视。

EN

回答 6

Stack Overflow用户

回答已采纳

发布于 2008-10-31 09:37:35

Update Q4 2017: as commented by vda8888,在Java9中,系统java.lang.ClassLoader不再是java.net.URLClassLoader

参见"Java 9 Migration Guide: The Seven Most Common Challenges

,我刚刚描述的类加载策略是在一种新类型中实现的,在Java9中,应用程序类加载器就是这种类型。

这意味着它不再是URLClassLoader,因此偶尔出现的(URLClassLoader) getClass().getClassLoader()(URLClassLoader) ClassLoader.getSystemClassLoader()序列将不再执行。

java.lang.ModuleLayer将是一种替代方法,用于影响模块路径(而不是类路径)。例如,参见"Java 9 modules - JPMS basics“。

对于Java 8或更低版本:

一些一般性的评论:

您不能(以一种保证工作的可移植方式,见下文)更改系统类路径。相反,您需要定义新的ClassLoader。

ClassLoaders以一种分层的方式工作...因此,对类X进行静态引用的任何类都需要装入与X相同的ClassLoader中,或者装入一个子ClassLoader中。您不能使用任何自定义ClassLoader来使由系统ClassLoader链接正确加载的代码,如果它以前没有这样做的话。因此,除了定位的额外代码之外,还需要安排在自定义ClassLoader中运行主要应用程序代码。

(也就是说,cracked-all在评论中提到了extending the URLClassLoader的这个例子)

您可以考虑不编写自己的ClassLoader,而只使用URLClassLoader。使用不在父类加载器url中的url创建一个URLClassLoader。

代码语言:javascript
复制
URL[] url={new URL("file://foo")};
URLClassLoader loader = new URLClassLoader(url);

more complete solution将为:

代码语言:javascript
复制
ClassLoader currentThreadClassLoader
 = Thread.currentThread().getContextClassLoader();

// Add the conf dir to the classpath
// Chain the current thread classloader
URLClassLoader urlClassLoader
 = new URLClassLoader(new URL[]{new File("mtFile").toURL()},
                      currentThreadClassLoader);

// Replace the thread classloader - assumes
// you have permissions to do so
Thread.currentThread().setContextClassLoader(urlClassLoader);

如果您假设JVM系统类加载器是一个URLClassLoader (并不是所有JVM都是这样),那么您也可以使用反射来实际修改系统类路径...(但这是一个黑客;)):

代码语言:javascript
复制
public void addURL(URL url) throws Exception {
  URLClassLoader classLoader
         = (URLClassLoader) ClassLoader.getSystemClassLoader();
  Class clazz= URLClassLoader.class;

  // Use reflection
  Method method= clazz.getDeclaredMethod("addURL", new Class[] { URL.class });
  method.setAccessible(true);
  method.invoke(classLoader, new Object[] { url });
}

addURL(new File("conf").toURL());

// This should work now!
Thread.currentThread().getContextClassLoader().getResourceAsStream("context.xml");
票数 80
EN

Stack Overflow用户

发布于 2008-10-31 08:49:32

我不相信你可以-正确的事情(我相信)是用新的路径创建一个新的类加载器。或者,您可以编写自己的类加载器,它允许您动态地更改类路径(用于该加载器)。

票数 3
EN

Stack Overflow用户

发布于 2011-07-20 19:57:47

页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/252893

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档