我的方法应该抛出自己的异常,还是让.NET抛出一个文件不存在?

时间:2015-10-05 14:36:49

标签: c# exception

这是我的代码:

public void ReadSomeFile(string filePath)
{
    if (!File.Exists(filePath))
        throw new FileNotFoundException();

    var stream = new FileStream(filePath, ....)
    .....
}

我应该自己抛出异常(参见File.Exists检查)吗?如果文件不存在,FileStream将会抛出FileNotFoundException。这里有什么好的编程习惯?代码分析说我们应该验证我们的参数。但是如果我将该参数直接传递给另一个方法(我的或其他代码)并且该方法本身会抛出异常,那么在我的代码中验证参数有什么好处呢?

4 个答案:

答案 0 :(得分:119)

if (File.Exists(f)) { DoSomething(f) }(或否定)是一种反模式。可以在这两个语句之间删除或创建文件,因此检查它的存在是没有意义的。

除此之外,正如评论中所指出的,虽然File.Exists()可能会返回true,但实际打开文件仍然会因各种原因而失败。因此,您必须重复错误检查并抛出文件的开头。

由于您不想重复自己,而是将代码保持为DRY,只需尝试打开文件并让new FileStream()抛出。然后你可以捕获异常,如果你愿意,可以重新抛出原始异常或抛出特定于应用程序的异常。

当然,调用File.Exists()是合理的,但不是这种模式。

答案 1 :(得分:15)

Your method is called ReadSomeFile and takes a filename as its input, therefore it is reasonable for it to throw a FileNotFoundException. As you cannot add any value by catching the exception then throwing it yourself, just let .NET throw it.

However if your method was LoadData(databaseName) and it has to access many files, catching the exception, and throwing a custom exception may be of value, as you could add the databaseName to the exception along with other helpful information.

答案 2 :(得分:1)

除了已经给出的答案,你还可以说这取决于你期望发生的事情。

如果你想读取一个日志文件并且它不存在,你想抛出一个错误,还是只是一个空字符串(或空字符串数组)?

如果返回一个默认值(如空字符串),我只需将函数内容包装在try-catch中(但仅用于预期的错误)并返回catch块中的默认值,同时返回try块中的实际内容。

这会留下三种可能的情况:

  1. 返回文件内容;
  2. 返回默认值,因为发生了预期错误;
  3. .NET引发错误,因为您没有捕获到该特定错误。

答案 3 :(得分:0)

在您不知道完整的情况下,让正确的方法尝试打开文件 文件名,某些特殊文件名(例如Device filesUNC paths):

在某些情况下,其他文件方法可能会失败,但打开文件成功。

特殊文件名的一些示例是:

  • CON
  • NUL
  • COM1,COM2,COM3,COM4
  • \\服务器\共享\ FILE_PATH
  • \\ teela \ admin $ \ system32(到达C:\ WINNT \ system32)
  • C:.. \ FILE.TXT
  • \\。\ COM1
  • %TEMP%
  • 以及......