Java 从FileReader更改为getResourceAsStream

Java 从FileReader更改为getResourceAsStream,java,filereader,Java,Filereader,当我尝试从一个.jar文件加载我的小游戏时,fileReader将不再工作,有人建议我使用getResourceAsStream函数,当我在IDE中运行下面的代码时,它可以正常工作,因此路径是正确的,当我更改为getResourceAsStream(当前已注释掉)并删除文件读取器行时,我得到这些错误 Exception in thread "Thread-0" java.lang.NullPointerException at java.io.Reader.<init>(Re

当我尝试从一个.jar文件加载我的小游戏时,fileReader将不再工作,有人建议我使用getResourceAsStream函数,当我在IDE中运行下面的代码时,它可以正常工作,因此路径是正确的,当我更改为getResourceAsStream(当前已注释掉)并删除文件读取器行时,我得到这些错误

Exception in thread "Thread-0" java.lang.NullPointerException
    at java.io.Reader.<init>(Reader.java:78)
    at java.io.InputStreamReader.<init>(InputStreamReader.java:72)
线程“thread-0”java.lang.NullPointerException中的异常 在java.io.Reader上。(Reader.java:78) 位于java.io.InputStreamReader。(InputStreamReader.java:72) 有没有办法解决这个问题

public class Utils {
    public static String loadFileAsString(String path) {
        StringBuilder builder = new StringBuilder();

        try{
            //InputStream is = Utils.class.getResourceAsStream(path);
            //BufferedReader br = new BufferedReader(new InputStreamReader(is));
            BufferedReader br = new BufferedReader(new FileReader(path));
            String line;
            while((line = br.readLine()) != null)
                builder.append(line + "\n");

            br.close();
        }catch(IOException e){
            e.printStackTrace();
        }
        return builder.toString();
    }
}

<?xml version="1.0" encoding="UTF-8"?>
<module type="JAVA_MODULE" version="4">
  <component name="NewModuleRootManager" inherit-compiler-output="true">
    <exclude-output />
    <content url="file://$MODULE_DIR$">
      <sourceFolder url="file://$MODULE_DIR$/src" isTestSource="false" />
      <sourceFolder url="file://$MODULE_DIR$/res" isTestSource="false" />
    </content>
    <orderEntry type="jdk" jdkName="1.8" jdkType="JavaSDK" />
    <orderEntry type="sourceFolder" forTests="false" />
    <orderEntry type="module-library">
      <library>
        <CLASSES>
          <root url="file://$MODULE_DIR$/res" />
        </CLASSES>
        <JAVADOC />
        <SOURCES />
      </library>
    </orderEntry>
    <orderEntry type="module-library" exported="">
      <library>
        <CLASSES>
          <root url="file://$MODULE_DIR$/res/worlds" />
        </CLASSES>
        <JAVADOC />
        <SOURCES />
      </library>
    </orderEntry>
  </component>
</module>
公共类Utils{
公共静态字符串loadFileAsString(字符串路径){
StringBuilder=新的StringBuilder();
试一试{
//InputStream is=Utils.class.getResourceAsStream(路径);
//BufferedReader br=新的BufferedReader(新的InputStreamReader(is));
BufferedReader br=新的BufferedReader(新文件读取器(路径));
弦线;
而((line=br.readLine())!=null)
builder.append(第+行“\n”);
br.close();
}捕获(IOE异常){
e、 printStackTrace();
}
返回builder.toString();
}
}

您需要开始了解自己在做什么,类路径是什么,Java如何加载类,以及应用程序是如何捆绑的

启动Java程序时,使用如下命令:

java -cp /some/directory:/some/file.jar com.foo.bar.Main
给定上述命令,java将尝试在两个位置加载主类(以及代码中使用的所有其他类):

  • /some/目录
    目录
  • jar文件
    /some/file.jar
由于类名为Main,并且位于包com.foo.bar中,因此它将查找名为
/some/directory/com/foo/bar/Main.class
的文件,如果找不到它,它将在jar文件中查找条目
/com/foo/bar/Main.class

当您使用
SomeClass.getResourceAsStream(“/res/worlds/world1.txt”)
时,它将应用相同的策略:查找文件
/some/directory/res/world1.txt
,如果找不到,请在jar文件中查找条目
/res/worlds/world1.txt

因此,由于您使用IDE来运行项目,您需要了解IDE是如何工作的:它使用什么命令来启动您的程序。原则很简单:

  • 有一个目标目录,IDE将从源.java文件生成的.class文件放在该目录中。运行IDE程序时,此目标目录是类路径的一部分
  • 还有一个目标目录,IDE在其中存储所有非.java文件的文件,这些文件位于IntelliJ中标记为“Resources root”的目录下。此目标目录也是类路径的一部分
目标目录中的结构始终尊重源/资源目录的结构

将应用程序打包为jar文件时,最终将得到一个jar文件,其中包含位于这些目标目录下的所有内容


默认情况下,在基本IntelliJ项目中,src目录也是资源根目录。因此,您放在那里的每个文件都会在目标目录中结束,因此在从IDE启动时以及在目标目录打包为jar时,都可以在类路径中使用。您应该将文件放在src目录下的某个地方,而不要弄乱依赖项。您的txt文件是项目源代码的一部分,就像Java文件一样。IDE通过将它与.class文件一起复制到目录来“编译”它

你的.jar文件在哪里?在我的桌面上和artifacts文件夹中运行它,结果相同。很抱歉,它应该是一个输出流,我认为它从文本文件读取数字时,仍然会导致错误。我的意思是,jar在类路径中吗?你可能传递了错误的路径。您想阅读的资源是什么?它在jar文件中的什么位置?你走的是哪条路?您是否阅读了Class.getResource[AsStream()]的javadoc以了解它的功能,以及它所期望的路径?