C# Try Catch Finally并非所有代码路径都返回值
在理想情况下,以下代码应执行标量sql命令:C# Try Catch Finally并非所有代码路径都返回值,c#,sql,C#,Sql,在理想情况下,以下代码应执行标量sql命令: public object AsScalar() { SqlCommand cmd = CreateSqlCommand(); try { cmd.Connection.Open(); return cmd.ExecuteScalar(); } catch (Exception exc) {
public object AsScalar()
{
SqlCommand cmd = CreateSqlCommand();
try
{
cmd.Connection.Open();
return cmd.ExecuteScalar();
}
catch (Exception exc)
{
log.Error("Exception caught for command: "+_sql, exc);
}
finally
{
Done(cmd);
}
}
但是,我从Visual Studio 2010收到以下错误:
not all code paths return a value
我认为在try-catch-finally中,无论是否捕获了异常,它都将始终执行finally语句,但情况似乎并非如此
当try finally正常工作时,为什么添加catch子句会导致此错误?实际上,
catch
块只是记录一条消息。它从不返回任何内容或抛出异常。因此,一个可能的执行路径是抛出异常,记录异常,然后。。。没有任何东西会被归还。实际上,将执行finally
块,但是那里也没有return
语句
要解决这个问题,您可以在
catch
块中抛出异常或返回null。我应该提到,回送通常应该是首选解决方案。对于catch
子句,如果抛出异常,您将捕获它,然后它不会从方法中传播出去。。。因此,执行将到达try/catch/finally块的末尾,到达方法的末尾,并且您将不会返回任何东西-糟糕
当您只有一个try/finally
语句时,您要么进入return
语句,要么抛出一个异常,该异常将从方法中传播出去——这两个都可以
如果要重新显示异常,可以使用:
catch (Exception exc)
{
log.Error("Exception caught for command: "+_sql, exc);
throw;
}
这将修复编译时错误,因为现在无法在不返回值或传播异常的情况下结束方法。然而,我通常不鼓励“log/throw/log/throw”链进入堆栈——只在顶层进行日志记录通常会更干净,不管最终捕获异常的是什么。如果要添加更多上下文,可以将其添加到现有异常中(有属性,尽管在我的经验中很少使用它),或者将此异常包装到另一个异常中。您需要有一个默认的return子句;编译器识别出
try
块可能会失败。除此之外,您不会返回任何值(或抛出异常)。无论是finally
还是catch
都不会返回任何内容……首先,感谢您的回答,您的回答肯定很有帮助,并使您更好地了解发生了什么,因此+1可以实现这一点。其次,从catch?@PseudoNym01返回一个空白或null对象,该对象将被编译,但在运行时,正如Jon解释的那样,这将意味着错误将被吃掉,这可能会导致应用程序处于未知/不安全状态。您应该正确处理sql异常,而不仅仅是假设它们可以被忽略。因此,这里最好的做法当然是将异常抛出。我的最终目标是优雅地处理异常,重新抛出异常是否会在应用程序本身内造成可能的崩溃?