我正在尝试创建一个文件,在此之前删除它(如果存在)。我的问题是,每当我有一个成功的删除操作,并在此之后立即尝试创建相同的文件夹,它失败与AccessDenied。方法描述(对于deleteIfExists和createDirectory)都没有提到这样的行为,所以我想我做错了。
这是代码:
package nio2;
import java.io.*;
import java.nio.file.*;
public class Test{
public static void main(String[] args)
{
Path existing = Paths.get("nio2//alpha//inner.txt"); // already existing
Path cpytarget = Paths.get("nio2//alphacpy//inner.txt"); // file to be created
Path target = Paths.get("nio2//alphacpy");//
try{
if(Files.exists(cpytarget))
{
Files.list(target).forEach(Test::WrappedDeleteIfExists); // deleting files inside folder
System.out.println("Deleting the directory if it exists - alphaCpy\t" + Files.deleteIfExists(target));//deleting
}
else
System.out.println("It does not exist, no need to delete anything");
System.out.println("Creating alphaCpy\t" + Files.createDirectory(target));//creating
System.out.println("copying inner.txt to the new directory\t" + Files.copy(existing,cpytarget));
}catch(IOException e)
{
e.printStackTrace();
}
}
public static void WrappedDeleteIfExists(Path in)
{
try{
System.out.println("Deleting files inside the folder\t" + Files.deleteIfExists(in));
}catch (IOException e)
{
e.printStackTrace();
}
}
}
所以成功运行(没有删除时)。这是输出
It does not exist, no need to delete anything
Creating alphaCpy nio2\alphacpy
copying inner.txt to the new directory nio2\alphacpy\inner.txt
如果我在文件夹和文件已经存在之后运行它,我会得到例外:
Deleting files inside the folder true
Deleting the directory if it exists - alphaCpy true
java.nio.file.AccessDeniedException: nio2\alphacpy
at sun.nio.fs.WindowsException.translateToIOException(WindowsException.java:83)
at sun.nio.fs.WindowsException.rethrowAsIOException(WindowsException.java:97)
at sun.nio.fs.WindowsException.rethrowAsIOException(WindowsException.java:102)
at sun.nio.fs.WindowsFileSystemProvider.createDirectory(WindowsFileSystemProvider.java:504)
at java.nio.file.Files.createDirectory(Files.java:674)
at nio2.Test.main(Test.java:19)
下次运行再次成功,因为它已被删除等等。那么问题是导致AccessDenied异常的原因是什么?请记住,文件未打开/使用,相对路径有效。
编辑:好的,我设法纠正了它,但说实话,我仍然无法向自己解释最初的问题。如果有人可以提供帮助,我将不胜感激。我从使用Stream转到File []以删除文件夹中的文件。在我这样做之后,它就像一个魅力。以下是更正后的代码:
public static void main(String[] args) throws InterruptedException
{
Path existing = Paths.get("E:/work/Java/Tests/alpha/inner.txt"); // already existing
Path cpytarget = Paths.get("E:/work/Java/Tests/alphacpy/inner.txt"); // file to be created
Path target = Paths.get("E:/work/Java/Tests/alphacpy");//
File fileTarget = new File("E:/work/Java/Tests/alphacpy");
try{
if(Files.exists(cpytarget))
{
WrappedDeleteIfExists(fileTarget.listFiles()); // CHANGED , no longer using Stream<Path> pipeline to go through the file list
// deleting files inside folder
System.out.println("Deleting the directory if it exists - alphaCpy\t" + Files.deleteIfExists(target));//deleting
}
else
System.out.println("It does not exist, no need to delete anything");
System.out.println(Files.exists(target));
System.out.println("Creating alphaCpy\t" + Files.createDirectory(target));//creating
System.out.println("copying inner.txt to the new directory\t" + Files.copy(existing,cpytarget));
}catch(IOException e)
{
e.printStackTrace();
}
}
// CHANGED - using File[] instead of Path
public static void WrappedDeleteIfExists(File[] in)
{
for(int i =0;i<in.length;i++)
{
System.out.println("Deleting files inside the folder\t" +in[i].delete());
}
}
显然,即使在完成之后,Stream操作也会以某种方式锁定它,但这不是IO流(或者它是否与Files.list()??),我可以关闭,所以我能做什么才能让它与Stream一起使用 - 它不是Closable或者试图强制GC的东西是有意义的。
答案 0 :(得分:0)
我注意到程序使用Files.list(dir)后跟Files.deleteIfExists(path)的类似问题。在VM退出之前,所有已删除的文件夹都不会从Windows资源管理器视图中消失,并且如果在Windows资源管理器中单击,直到VM退出时,将拒绝访问。
我的程序只是通过在使用后关闭每个Files.list()流来修复,最好是使用try(resource)... finally。然后,Windows资源管理器会立即与每次删除同步,而不是等到VM退出
try(Stream<Path> str = Files.list(target))
{
// do your str.forEach() calls with Files.deleteIfExists
}
finally
{
}