【问题标题】:Beginner Q: how to open a file in Java and keep it open初学者问:如何用Java打开文件并保持打开状态
【发布时间】:2017-11-01 09:19:00
【问题描述】:

这只是一个简单的Java命令行独立程序。

我想打开一个要写入的文件,并保持打开状态。我需要以人类可读的 ASCII 格式向其写入格式化的浮点数/双精度数,例如 CSV 文件。

我尝试了各种方法(1)(2)(3)我通过我最喜欢的搜索引擎找到了,它们有以下形式:

try {
   // some file handle opening sequence
}
catch ( <some exception> ) {
  // do something
}
finally {
  // do something else
}

(...或者在第三个示例的情况下,文件打开/写入/关闭在引发异常的函数内。)我意识到确保您已经打开文件是一种很好的编程风格,但出于我的目的,这真的没有必要。

无论如何,上述方法的问题是在 try{} 块之外,文件句柄被关闭。我想让它保持打开状态,因为我的代码的内核由一个巨大的循环组成,我经历了几十万次(比如说),每次通过我都想输出一个浮点数(ASCII 格式)到文件。

使用上面的表单,唯一的方法就是将我巨大的 for 循环包含在 try{} 块中。这似乎很愚蠢。或者,我可以每次通过循环重新打开文件,但这意味着额外的逻辑,第一次将文件作为“新”文件打开,并在所有后续时间中追加。

有什么方法可以打开文件,保持打开状态以偶尔写入,然后在我完成后关闭它?

类似:

{
// open file "data.out"
}
for (i=0;i<100000;i++) {
   // do a lot of stuff
   //
   // calculate some quantity "x"
   //
   // output float "x" in ASCII form, appending it to data.out
}
{
// close data.out
}

Java 允许这样做吗?谢谢。

【问题讨论】:

  • 唯一的办法就是在 try{} 块中包含我巨大的 for 循环。这似乎很愚蠢。这有什么“愚蠢”的?
  • 您也可以在文件末尾打开一个文件进行写入,信息将被追加而不被覆盖。public FileWriter(File file, boolean append)
  • 也许“傻”这个词是不明智的,但我不想把我的大循环放在另一个封闭块中的原因是它往往会降低人类可读性,因为循环可能里面有 1000 行代码,我必须扫描代码以查找匹配的大括号,我以后可能会决定我不仅要打开一个文件,还要打开两个或三个甚至更多要写入的文件。如果您的大循环在连续的 try{} 块中向下嵌套三个或更多层,那么在某些时候确实会变得很麻烦。
  • 然后您应该将 1000 行代码拆分为几种人类可读的方法。只需将调用者方法包装在 try/catch 块中即可。
  • 除了同意@JeremyGrand 之外,您的 IDE 以及您的源代码格式应该可以帮助您可视化和导航匹配的大括号。

标签: java file csv


【解决方案1】:

当然,您可以将 FileWriter 简单地存储在某个地方,就像任何其他变量一样。例如,您可以将整个编写逻辑封装在其自己的类中,该类为您指定的格式提供一个write 方法。

但是为什么看起来很傻?也许这种方法可能会有所帮助...

public void methodA(File myFile) throws IOException{
  try ( FileWriter writer = new FileWriter( myFile ) ) {
     writeTo(writer);
  }
}

private void writeTo(FileWriter writer) throws IOException {
   for (i=0;i<100000;i++) {
   // do a lot of stuff
   //
   // calculate some quantity "x"
   //
   // output float "x" in ASCII form, appending it to data.out
}

}

这样,一种方法负责打开/关闭/异常,而另一种方法可以使用赋予它的 FileWriter 专注于重要的写作内容。

【讨论】:

    【解决方案2】:

    正如你所说,文件在 try 块的末尾关闭。可能 FileWriter 对象在 try 块内创建: (你没有发布真正的java代码,只是一个伪代码。)

    示例,希望对您有所帮助

    public static void main(String[] args) 
    {
    ...
    BufferedWriter ofs=null; // should by outside the try block
    
    try
    { 
     Path logfile = Paths.set("C:\\temp\\log.log");
    
     ofs = Files.newBufferedWriter(logfile); // new in java 8
    
     YourWorker.doYourJob(ofs);
    
    } catch (Exception e)
    {   e.printStackTrace();
    } finally
    {
      if (ofs!=null) { try { ofs.close(); } catch (Exception e) {}   }
    }
    System.exit(1);     
    } //---------- end of main()
    } //---- end of class
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2011-04-24
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多