【问题标题】:java.io.FileNotFoundException even when the file path is correctjava.io.FileNotFoundException 即使文件路径正确
【发布时间】:2020-07-02 12:21:33
【问题描述】:

我使用的代码:

package play;

import java.io.File;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.IOException;
import java.io.InputStream;
import java.net.URL;

public class Play {

    InputStream music;
    public Play() {
    URL url=getClass().getResource("/music/Whitewoods - College Kill Dream.mp3");
    System.out.println(url.toString());
    try {
        FileInputStream fileInputStream=new FileInputStream(new File(url.toString()));
        fileInputStream.close();
    } catch (IOException e) {
        // TODO Auto-generated catch block
        e.printStackTrace();
    }
        
    }
    public static void main(String args[]) {
        new Play();
        
    }
    
    
    
}

上面的代码下面的行:

System.out.println(url.toString());

prints :
file:/C:/Users/eclipse-workspace/audioboard/bin/music/Whitewoods%20-%20College%20Kill%20Dream.mp3

如果我直接复制它并将其放入 chrome 的 url 放置框中。文件打开,但行:

FileInputStream fileInputStream=new FileInputStream(new File(url.toString()));

给出文件未找到错误。

错误堆栈:

java.io.FileNotFoundException: file:\C:\Users\eclipse-workspace\audioboard\bin\music\Whitewoods%20-%20College%20Kill%20Dream.mp3 (The filename, directory name, or volume label syntax is incorrect)
    at java.base/java.io.FileInputStream.open0(Native Method)
    at java.base/java.io.FileInputStream.open(FileInputStream.java:213)
    at java.base/java.io.FileInputStream.<init>(FileInputStream.java:155)
    at play.Play.<init>(Play.java:17)
    at play.Play.main(Play.java:26)

谢谢你的帮助。

【问题讨论】:

    标签: java audio mp3 audio-player jlayer


    【解决方案1】:

    您可以使用File 构造函数File(URI uri) 将您的URL url 转换为URI 并将其作为File 构造函数的参数传递,如下所示:

    File file = new File(url.toURI());
    

    【讨论】:

      【解决方案2】:

      file: 位使您看到的实际上不是文件路径,而是 URL。

      URL 有 toFile() 方法,它更接近您想要的,但仍然不是您真正想要的,即 getResourceAsStream

      1. 调用getResource/getResourceAsStream 的适当方式是Play.class.getResource,而不是getClass().getResource。一个小问题; getClass() 变体是非惯用的,并且严格来说更差/可读性更差:如果 Play 曾经被子类化,它会中断,而 Play.class.getResource 不会。即使它不相关,最好使用更惯用的样式,正确的答案是更多场景。

      2. 一般来说,如果你把你得到的资源转换成一个你搞砸的文件; getResource 的重点是为您提供来自您的类所在位置的资源,并且它们不必是文件。它们可以是 jar 中的条目(它们本身不是文件,并且不能作为 java.io.Filejava.nio.path.Path 直接访问),通过网络拉入,动态生成 - 任何事情都会发生,这就是抽象的重点。在这种情况下,您将获取文件并立即将其转换为InputStream。不要那样做 - getResource 抽象可以做到这一点。

      3. 像所有资源一样,您不能像这样打开输入流。无论发生什么,您都需要确保它也已关闭。使用 try-with-resources 来确保这一点。

      把它们放在一起:

      String songName = "Whitewoods - College Kill Dream.mp3";
      try (var in = Play.class.getResourceAsStream("/music/" + songName)) {
         //  .... do something with 'in' here. It is an InputStream.
      }
      

      无需关闭; try 构造会为你处理它。不管代码如何“退出”这些大括号(通过运行到它的末尾,通过return 或其他一些控制流,或通过异常) - 输入流将被关闭。

      【讨论】:

        猜你喜欢
        • 2018-09-16
        • 1970-01-01
        • 2021-08-13
        • 1970-01-01
        • 2019-01-04
        • 2018-12-10
        • 2013-07-16
        • 2017-05-26
        • 2022-11-16
        相关资源
        最近更新 更多