如何更改该包中存在的文件的数据?(在java中,如何获取该文件的outputStream?)

时间:2013-09-10 05:42:28

标签: java outputstream

我已经使用ResorceLoder类来获取输入流但是如何获得outputStream,这是否可以修改该包中的数据?(我需要使用java类更改该包中存在的图像文件存在于同一个jar文件中)

3 个答案:

答案 0 :(得分:3)

您无法在运行时直接更改jar文件的资源。 ClassLoader(给你那些InputStreams不提供OutputStream来重写jar文件中的文件)。

如果您想在运行时操作图像或资源,请不要将它们放在jar文件中,而是从文件系统中检索它们。

答案 1 :(得分:2)

更改类路径资源要么很困难要么不可能......取决于类加载器和类路径。

  • 如果类路径资源位于filesystem目录中,您应该可以替换它。但是,文件可能已锁定,并且无法保证在重新启动JVM之前更新的资源可见。

  • 如果类路径资源在本地文件系统中的JAR或ZIP中,则还有其他一些问题:

    1. 您无法对JAR或ZIP文件进行就地更新。您必须创建一个新的ZIP / JAR并将现有内容复制到其中。

    2. 类路径上的ZIP或JAR文件将被锁定。

  • 如果类路径资源位于已下载的ZIP或JAR中,则无法(通常)在源代码更新文件...因此您的更改可能不会“粘住”。

  • 如果您使用的是自定义类加载器,则所有投注均已关闭...

简而言之,最好找到一种不同的方法来做到这一点;例如将资源复制/安装到文件系统中的可写目录中,然后从那里访问它们。

答案 2 :(得分:0)

好的..如果我正确理解了您的问题,您希望通过位于同一位置的程序文件更改类路径中的资源。我认为,如果你理解以下限制,那不应该是一个问题:

  1. 类加载器永远不会给你一个资源句柄(位于jar中)作为带有目录路径的文件和所有文件。这是因为Jar通常不会爆炸。您需要以爆炸形式获取jar,以便将资源作为文件获取。

  2. 运行程序时,当前工作目录可能不是类路径中资源/ jar的位置。

  3. 您需要弄清楚资源的目录,然后您可以轻松修改或执行您想要的操作。

  4. 一种方法是在可配置文件中的某处声明资源路径。这是一个非常简单的方法。

  5. 其他方法是使用逻辑找出路径。其中一个例子来自this link

    try {
    
    //Attempt to get the path of the actual JAR file, because the working directory is frequently not where the file is.
    
      //Example: file:/D:/all/Java/TitanWaterworks/TitanWaterworks-en.jar!/TitanWaterworks.class
    
     //Another example: /D:/all/Java/TitanWaterworks/TitanWaterworks.class
    
     PROGRAM_DIRECTORY = getClass().getClassLoader().getResource("TitanWaterworks.class").getPath(); 
    
     // Gets the path of the class or jar.
     //Find the last ! and cut it off at that location. If this isn't being run from a jar, there is no !, so it'll cause an exception, which is fine.
    try {
        PROGRAM_DIRECTORY = PROGRAM_DIRECTORY.substring(0, PROGRAM_DIRECTORY.lastIndexOf('!'));
    } catch (Exception e) { }
    
     //Find the last / and cut it off at that location.
    PROGRAM_DIRECTORY = PROGRAM_DIRECTORY.substring(0, PROGRAM_DIRECTORY.lastIndexOf('/') + 1);
    //If it starts with /, cut it off.
    if (PROGRAM_DIRECTORY.startsWith("/")) PROGRAM_DIRECTORY = PROGRAM_DIRECTORY.substring(1, PROGRAM_DIRECTORY.length());
    //If it starts with file:/, cut that off, too.
    if (PROGRAM_DIRECTORY.startsWith("file:/")) PROGRAM_DIRECTORY = PROGRAM_DIRECTORY.substring(6, PROGRAM_DIRECTORY.length());
     } catch (Exception e) {
       PROGRAM_DIRECTORY = ""; //Current working directory instead.
     }