繁体   English   中英

FileNotFound(拒绝访问)java.io上的异常

[英]FileNotFound (Access is denied) Exception on java.io

运行此程序时为什么会出现此错误? 这发生在随机迭代之后。 通常在第8000次迭代之后。

public static void main(String[] args)
{
    FileWriter writer = null;
    try
    {
        for(int i = 0; i < 10000; i++)
        {
            File file = new File("C:\\Users\\varun.achar\\Desktop\\TODO.txt");

            if(file.exists())
            {
                System.out.println("File exists");
            }
            writer = new FileWriter(file, true);
            writer.write(i);
            System.out.println(i);
            writer.close();
            if(!file.delete())
            {
                System.out.println("unable to delete");
            }

            //Thread.sleep(10);
            //writer = null;
            //System.gc();
        }
    }
    catch(IOException e)
    {
        e.printStackTrace();
    }
    finally
    {
        if(writer != null)
        {
            try
            {
                writer.close();
            }
            catch(IOException e)
            {
                e.printStackTrace();
            }
        }
    }
}

发生异常后,该文件不存在。 这意味着它正在删除,但FIleWriter尝试在此之前获取锁,即使它不是多线程程序。 是因为Windows没有足够快地删除文件,因此FileWriter没有锁定? 如果是这样,那么file.delete()方法在Windows实际删除之前返回?

我如何解决它,因为我在负载测试我的应用程序时遇到了类似的问题。

编辑1:Stacktrace:

java.io.FileNotFoundException: C:\Users\varun.achar\Desktop\TODO.txt (Access is denied)     
at java.io.FileOutputStream.openAppend(Native Method)
    at java.io.FileOutputStream.<init>(FileOutputStream.java:192)
    at java.io.FileOutputStream.<init>(FileOutputStream.java:116)
    at java.io.FileWriter.<init>(FileWriter.java:61)

编辑2 :在程序中添加了file.exists()和file.delete条件。 和新的堆栈跟踪:

7452
java.io.FileNotFoundException: C:\Users\varun.achar\Desktop\TODO.txt (Access is denied)
    at java.io.FileOutputStream.openAppend(Native Method)
    at java.io.FileOutputStream.<init>(FileOutputStream.java:192)
    at java.io.FileWriter.<init>(FileWriter.java:90)
    at com.TestClass.main(TestClass.java:25)

编辑3线程转储

TestClass [Java Application]    
    com.TestClass at localhost:57843    
        Thread [main] (Suspended (exception FileNotFoundException)) 
            FileOutputStream.<init>(File, boolean) line: 192    
            FileWriter.<init>(File, boolean) line: 90   
            TestClass.main(String[]) line: 24   
    C:\Users\varun.achar\Documents\Softwares\Java JDK\JDK 6.26\jdk\jre\bin\javaw.exe (09-Nov-2011 11:57:34 PM)  

编辑4 :程序在具有相同操作系统的不同机器上成功运行。 现在,我如何确保应用程序在部署的计算机中成功运行?

在任何操作系统上,您一次只能拥有一定数量的打开文件/线程。 您似乎达到了操作系统限制。 尝试在循环内将文件设置为null。

我有同样的问题,一个java程序(单线程)打开,删除然后连续重新打开同一个文件。

在某些Windows系统上,我们遇到了与此处报告的相同的问题,在Linux,Solaris和其他各种Windows系统上,它可以正常工作。

使用SysInternals Process Monitor(现在为MS)跟踪程序,清除删除首先在操作系统级别完成,并清除后续打开失败并显示PENDING DELETE状态。

因此,在实际删除文件之前,OS / NTFS /磁盘级别似乎有一些轻微的延迟,这似乎是我们案例中随机失败的原因。

作为一种解决方法,我改变了.delete()调用,而只是在其顶部写入新的FileWriter(文件),这似乎正在起作用。

所有系统都没有出现这个问题,一个总是会失败的特定型号,都是在没有固定数量的循环之后,是带有WD Smartdrive的Windows 7 /戴尔Lattitude E6420,而我的Windows 7 /戴尔精密M4600(带有固态)国家驱动器)或T3400与Linux我从来没有遇到过这个问题。

干杯 - 马克

如果我正确理解您的堆栈跟踪,则在尝试创建新的FileWriter时会出现异常。 如果不进一步调查,就不可能知道原因。

  • 返回值可能会说明问题。 特别是,检查File.delete()返回的内容。
  • 在尝试创建新的FileWriter之前,请检查File.exists()返回的内容。

如果前一个delete()返回true并且在它之后的exists()也返回true ,那么在单线程程序中,那确实是奇怪的。

编辑:所以似乎删除成功,之后文件不存在。 当然,它应该是如何工作的,所以FileWriter抛出异常的原因很奇怪。 再想一想,尝试检查File.getParentFile().canWrite() 也就是说,你写入目录的权限会以某种方式消失。

编辑2:

不要在具有相同操作系统的其他计算机上获取错误。 现在,我如何确保在部署它的应用程序中不会出现此错误?

到目前为止,您有台工作正常, 一台工作正常。 也许你可以在更多机器上试试。 第一台机器可能会以某种方式损坏并导致错误。 令人惊讶的是,数字计算机及其程序(我的意思是操作系统和Java,不一定是你的程序)经常可能只是“有点破碎”,因此它们几乎在所有时间都能完美地工作,但是随着一些特定的硬件随机失败&用例 - 通常在负载很重的情况下 - 类似于多线程程序的错误行为。 成为你的问题不一定是你的错:-)

坦率地说, 确保机器X中不会出现错误的唯一方法是在机器X上运行程序。不同的东西,如快速连续创建和删除相同文件8000次,很容易出错,即使它“应该管用。 计算机,操作系统和API 并不完美。 你做的越不寻常的东西越多,瑕疵就越容易实现,因为不正常的使用通常不如日常操作那么彻底。

你能有条件地尝试写入文件吗?

使用file.exists然后写入它,这样您就可以避免任何其他问题。 很难说这个例外。

http://download.oracle.com/javase/6/docs/api/java/io/File.html#exists ()

您是否也可以在此时发布一个线程转储,只是为了进一步调试它。

在再次写作之前,请冲洗作者。

这可能是一个很长的镜头,但是,你可以尝试使用一个不直接放在桌面上的文件。 代替:

"C:\\Users\\varun.achar\\Desktop\\TODO.txt"

尝试:

"C:\\Users\\varun.achar\\SomeOtherDirectory\\TODO.txt"

操作系统可能会在这里用所有桌面挂钩杀死你......

根据评论编辑:

  • “坏”机器上是否有预定的作业?
  • 而不是调试环境,你有一个系统管理员来做到这一点?
  • 这是否适用于干净的 Windows安装? [95%的可能性]
  • 由于根本原因似乎是环境,而不是解决Windows配置问题,您是否能够继续执行其他任务,并将其留给那些保留系统之间差异列表的人?

我只是遇到了同样的问题(FileWriter&Access Denied)。

我猜的原因是:Windows 7对文件进行了锁定,因为在资源管理器窗口中显示了文件内容的预览(在窗口中选择了该文件)。

解决方案:我在资源管理器窗口中取消选择了该文件。 并且IOException消失了。

这些是在删除文件之前应该处理的场景http://www.java2s.com/Code/Java/File-Input-Output/DeletefileusingJavaIOAPI.htm

至少检查程序中的返回值。

感谢大家的帮助,但最终解决了这个问题。

public static void main(String[] args)
    {
        FileWriter writer = null;
        try
        {
            for(int i = 0; i < 10000; i++)
            {
                File file = new File("C:\\tenant-system-data\\abc.txt");
                if(!file.getParentFile().canWrite())
                {
                    System.out.println("parent file error");
                }
                if(file.exists())
                {
                    System.out.println("File exists");
                }
                int count = 0;
                while(count++ < 5)
                {
                    try
                    {
                        file.createNewFile();
                        break;
                    }
                    catch(IOException e)
                    {
                        try
                        {
                            Thread.sleep(100);
                        }
                        catch(InterruptedException e1)
                        {
                            e1.printStackTrace();
                        }

                    }
                }
                writer = new FileWriter(file, true);
                writer.write(i);
                System.out.println(i);
                writer.close();
                if(!file.delete())
                {
                    System.out.println("unable to delete");
                }

                //Thread.sleep(10);
                //writer = null;
                //System.gc();
            }
        }
        catch(IOException e)
        {
            e.printStackTrace();
        }
        finally
        {
            if(writer != null)
            {
                try
                {
                    writer.close();
                }
                catch(IOException e)
                {
                    e.printStackTrace();
                }
            }
        }
    }

您在目录中具有删除权限,但没有创建权限。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM