我想知道Class.getResource()和之间的区别是什么ClassLoader.getResource()?
编辑:我特别想知道文件/目录级别是否涉及任何缓存.如"在类版本中缓存的目录列表?"
以下AFAIK应该基本上做同样的事情,但它们不是:
getClass().getResource()
getClass().getClassLoader().getResource()
Run Code Online (Sandbox Code Playgroud)
我在摆弄一些报告生成代码时发现了这一点,该代码WEB-INF/classes/从该目录中的现有文件创建了一个新文件.当使用Class中的方法时,我可以找到部署时使用的文件getClass().getResource(),但在尝试获取新创建的文件时,我收到了一个null对象.浏览目录会清楚地显示新文件存在.文件名前面带有正斜杠,如"/myFile.txt"中所示.
另一方面,ClassLoader版本getResource()确实找到了生成的文件.根据这种经验,似乎存在某种目录列表的缓存.我是对的,如果是的话,这会记录在哪里?
从API文档上Class.getResource()
查找具有给定名称的资源.搜索与给定类关联的资源的规则由类的定义类加载器实现.此方法委托给此对象的类加载器.如果此对象由引导类加载器加载,则该方法委托给ClassLoader.getSystemResource(java.lang.String).
对我来说,这是"Class.getResource真正调用它自己的类加载器的getResource()".这和做的一样getClass().getClassLoader().getResource().但显然不是.有人可以请我为此事提供一些启示吗?
从IDEA 2018.2.1开始,IDE从模块化的依赖项开始错误突出显示"不在模块图"中的包.我module-info.java在项目中添加了一个文件并添加了必需的requires语句,但我现在无法访问src/main/resources目录中的资源文件.
(有关完整示例,请参阅此GitHub项目.)
当我使用./gradlew run或./gradlew installDist+生成的包装器脚本时,我能够读取资源文件,但是当我从IDE运行我的应用程序时,我不是.
我向
JetBrains 提出了一个问题,我学到的是IDEA正在使用模块路径,而Gradle默认使用类路径.通过向我添加以下块build.gradle,我能够让Gradle 也 ...无法读取任何资源文件.
run {
inputs.property("moduleName", moduleName)
doFirst {
jvmArgs = [
'--module-path', classpath.asPath,
'--module', "$moduleName/$mainClassName"
]
classpath = files()
}
}
Run Code Online (Sandbox Code Playgroud)
我尝试export将我感兴趣的资源目录作为"包",并在编译时遇到构建失败:
错误:包是空的或不存在:mydir
使用opens而不是exports获得相同的错误,但降级为警告.
我甚至尝试移动mydir资源目录src/main/java,但是这产生了相同的错误/警告,并且还导致资源没有被复制到build目录中.
应该在Java 9中使用哪些资源,以及如何访问它们?
注意:在继续研究问题之后,我已经相当大地编辑了这个问题.在最初的问题中,我还试图弄清楚如何在资源目录中列出文件,但在调查过程中我确定这是一个红色的鲱鱼 - 首先,因为阅读资源目录只有在资源是从file:///URL 读取(也许甚至不是),第二,因为普通文件也没有工作,所以很明显问题是资源文件一般而不是专门用于目录.
解:
按照Slaw的回答,我将以下内容添加到build.gradle:
// at compile …Run Code Online (Sandbox Code Playgroud) 我试图让我的应用程序与Java 9一起运行,但不幸的是,当它尝试使用加载资源时,其中一个普通的jar依赖项classLoader.getResource(name)会获得null.
当然,这适用于Java 8.
我使用模块文件声明了对相关模块的依赖,通过其jar名称引用模块的名称(糟糕),并使用该--module-path选项添加jar原样(没有Java 9的自定义).
这是我的近似模块文件声明:
module my.mod {
requires ivy; // the file is called ivy-2.4.0.jar
}
Run Code Online (Sandbox Code Playgroud)
我用这个命令运行:
java --module-path my-mod.jar:ivy-2.4.0.jar -m my.mod
Run Code Online (Sandbox Code Playgroud)
当我运行应用程序时,如果库不尝试加载该资源,它可以正常工作......但如果它运行,它会NullPointerException在它尝试使用该资源的行处获得一个.
我可以看到资源存在于jar文件中的正确路径中.
我已经尝试将我的应用程序作为jar运行(如上所示)并且只运行类文件:
java --module-path modules-dir:ivy-2.4.0.jar -m my.module/my.Main
Run Code Online (Sandbox Code Playgroud)
在后一种情况下,错误是不同的,但相关:Ivy甚至找不到它试图从自己的jar加载的属性文件!
有没有解决方法,这是一个已知的错误,还是我做错了什么?
我在 Eclipse 中有一个 gradle 项目。这是我的项目的结构
我在 .cssstyleclass.css中有 css 资源scr/main/resources/css。首先我尝试使用访问它
scene.getStylesheets().add("css/styleclass.css");
Run Code Online (Sandbox Code Playgroud)
但是我收到警告resource not found.我也通过删除module-info.java文件来尝试它。但结果是一样的。
然后我尝试使用
String urlString = ComboBoxStyling.class.getClassLoader().getResource("css/styleclass.css").toExternalForm();
Run Code Online (Sandbox Code Playgroud)
问题是,如果我删除moduele-info.java并应用样式表,这条线会起作用。但是随着module-info.java我收到空指针异常。
我知道的不多,但至少我知道类加载器在 Java 9 中有变化。那么我如何在 Java 9 中做同样的事情。我的module-info.java文件包含以下内容
module pk.training.basit {
exports pk.training.basit;
requires transitive javafx.controls;
}
Run Code Online (Sandbox Code Playgroud)
感谢和问候
巴斯特·马哈茂德·艾哈迈德
我在尝试从外部模块的资源文件夹加载资源文件时遇到困难。我正在使用 IntelliJ,我们的项目是使用 Maven 构建的。
使用模块之前的原始代码是这样的:
getClass().getResourceAsStream(rulesFile)
这现在产生了null结果。
模块的结构如下:
client
- java
- org.example.client
- Controller.java
data
- java
- ...
- resources
- org.example.data.files
- rulesFile
Run Code Online (Sandbox Code Playgroud)
在模块中client:
getClass().getResourceAsStream(rulesFile) 不起作用。
但是,如果我尝试去做ModuleLayer.boot().findModule("data").get().getResourceAsStream(rulesFile),那么它工作正常。
我的问题是,是否可以使模块内部rulesFile可见,以便可以使用普通的类加载器?我想避免必须明确指定它来自的模块名称,因为在其他地方使用了从模块加载文件的类似代码。Controller.javaclientdata
我有哪些选项可以避免显式给出模块名称?
我尝试将以下内容添加到data模块文件中,但没有成功:
opens org.example.data.files to client
谢谢您的帮助!
简单的Java程序:
public static String loadText(String file) {
StringBuilder finalString = new StringBuilder();
InputStream in = null;
BufferedReader reader = null;
InputStreamReader isr = null;
try{
System.out.println("Text File: " + file);
// Version 1
//URL url = Thread.currentThread().getClass().getResource(file);
//in = url.openStream();
// Version 2
in = Class.class.getResourceAsStream(file);
isr = new InputStreamReader(in);
reader = new BufferedReader(isr);
String line;
while((line = reader.readLine()) != null) {
finalString.append(line).append("//\n");
}
}
catch(IOException e) {
e.printStackTrace();
System.exit(-1);
}
finally {
try {
if (isr != null) { …Run Code Online (Sandbox Code Playgroud)