Java nio文件系统监视器锁定目录。删除变得不可能。

8
我正在使用Java7的新功能来监视目录变化(如下面的教程所述:http://download.oracle.com/javase/tutorial/essential/io/notification.html)。监视本身工作正常(几乎没有问题)。
我有两个问题,希望你们中的一些人能够提出解决方法。
1. 在文件夹添加到监视器后,VM可以访问它并且不会释放它。这不应该是一个大问题,但如果您在另一个目录中创建一个目录,并在其中创建更多目录(例如,在目录中创建目录,并在中创建目录()),则无法删除目录,因为VM访问和。如果您想删除所有文件夹(例如,使用Windows资源管理器),您必须先删除,然后,然后。这很奇怪,但这种方式可以工作(尽管不方便)。
2. 这个问题似乎是第一个问题的结果。如果
中发生了许多更改,有时会得到一个异常,告诉我新创建的文件夹正在被另一个进程使用,无法访问它。这很奇怪,因为我认为这不应该影响通知的接收。而且由于不完全清楚什么时候会抛出此异常。
你有什么想法,如何使其不锁定或至少让用户以传统方便的方式删除这样的目录结构?
2个回答

2

我尝试了你发布链接中展示的代码,做了与你尝试的相同的事情:

在我的c:\temp目录中,我通过编程方式创建了c:\temp\a目录,然后是c:\temp\a\b目录:

File startDir = new File("c:\temp");
        if(!startDir.exists()) {
            startDir.mkdir();
        }
        File aDir = new File("c:\\temp\\a");
        File bDir = new File("c:\\temp\\a\\b");
        if(!aDir.exists()) {
            aDir.mkdir();
        }
        if(!bDir.exists()) {
            bDir.mkdir();
        }

然后我向 "a" 和 "b" 目录添加观察器:
public static void watch(final File dir,final WatchService watcher) {
        Path path = dir.toPath();
        try {
            final WatchKey bDirWatchKey = path.register(watcher, StandardWatchEventKinds.ENTRY_MODIFY);
            new Thread(new Runnable() {
                public void run() {
                    System.out.println("Watching: "+dir.getName());
                    while(true) {
                        try {Thread.sleep(1000);} catch (InterruptedException e) {}
                        List<WatchEvent<?>> events = bDirWatchKey.pollEvents();
                        for(WatchEvent<?> event:events) {
                            System.out.println(dir.getName()+" event: #"+event.count()+","+event.kind()+" File="+event.context());
                        }
                    }                   
                }
            }).start();
        } catch (IOException x) {
            x.printStackTrace();
        }
    }

如果我修改“a”或“b”中的文件,我可以得到相应的控制台输出,这个功能还不错。

确实,在Windows资源管理器(在Windowx XP机器上)中,我无法删除已监视的目录(它告诉我我没有访问权限)。但是我可以使用其他工具(如Total Commander)删除它。我甚至可以从Windows命令行中使用rd c:\temp\a\b删除它们。我认为这更多是Windows资源管理器的问题,而不是Java的问题...


-1
关于您的第二个问题,如果您遇到了“新创建的文件夹正在被其他进程使用,无法访问”的异常。您可以尝试在代码中使用原子操作。这将有助于操作不被中断,并且可能解决您的问题。

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接