try/catch块中finally子句的正确使用
本文关键字:子句 catch 块中 finally try | 更新日期: 2023-09-27 18:02:13
我试图找出"最佳"方式执行(关闭)语句在我的sql数据访问层方法。
我想知道这两种方式中哪一种被认为是更正确的(谢谢):
选项# 1
public void dbOperation( ... )
{
try
{
_cmd.Open();
_cmd.Execute();
}
catch (Exception ex)
{
throw ex;
}
finally
{
_cmd.Close()
}
}
选项# 2
public void dbOperation( ... )
{
try
{
_cmd.Open();
_cmd.Execute();
}
catch (Exception ex)
{
_cmd.Close()
throw ex;
}
_cmd.Close();
}
都不对。您不应该让catch
子句再次重新抛出异常,清除其堆栈跟踪,而不做任何有意义的事情,这是您的第一个选项所做的。
你应该只是结束在finally:
try
{
_cmd.Open();
_cmd.Execute();
}
finally
{
_cmd.Close()
}
第二个代码段也有同样的问题,因为你不正确地重新抛出了异常。
最好的选择是使用using
,它只是一个没有catch的try/finally的语法糖:
using(var command = ...)
{
command.Open();
command.Execute();
}
这还有一个额外的好处,即确保命令的作用域与有效使用命令时的作用域完全相同。try/finally块要求命令在被处理后是一个有效的标识符。
选项#1是两个选项中唯一正确的。实际上,您可以使用更少的代码获得与选项#1等效的内容:
try
{
_cmd.Open();
_cmd.Execute();
}
finally
{
_cmd.Close()
}
如果一个异常被抛出,没有必要有一个catch
块只是重新抛出它。如果您希望在catch
块中执行某些操作,例如记录异常,请确保这样做:
try
{
_cmd.Open();
_cmd.Execute();
}
catch (Exception ex)
{
logException(ex);
throw; //Just say throw, not throw ex, to preserve the original stack trace
}
finally
{
_cmd.Close()
}
选项#1。如果你使用option2,你将不会执行cmd。关闭,除非抛出异常