我发现了一个exception! 怎么办?

我已经开始使用try catch块(有点迟了,我知道!),但是现在我不确定一旦我发现exception,我不知道该怎么做。 我该怎么办?

Try connection.Open() Dim sqlCmd As New SqlCommand("do some SQL", connection) Dim sqlDa As New SqlDataAdapter(sqlCmd) sqlDa.Fill(dt) Catch ex As SQLException ' Ahhhh, what to do now!!!? Finally connection.Close() End Try 

exception处理的经验法则 – 如果你不知道如何处理它,不要抓住它。

按照经验法则进行exception处理 – 在最后一个负责任的时刻处理exception。 如果你不知道这是否是最后一个负责任的时刻,那不是。

你想要做什么? 这完全取决于你的应用程序。

你可以重试,你可以在屏幕上显示一个消息框,写入日志,可能性是无止境的。

作为一名开发人员,您无法预测每一个可能的错误 即使你不知道如何解决错误,在通用的catch代码中也是一个好主意。 您可能会保存到数据库中,并且可能会发生50个数据库错误之一,您将无法编写代码来处理每个错误。

你应该加上一个通用的方法,以确保你的程序不会简单地崩溃 ,在某些情况下只显示错误并让他们再去一次就足够了。 想象一下,如果原因是“磁盘已满”。 你只能打印出exception,让用户再试一次 – 他们知道该怎么做,然后自己解决问题。

这就是为什么我不同意关于如果你不知道该怎么做的话,不处理它的评论。 你应该总是处理它,即使只是显示一个消息框,说'错误',因为它比“这个程序执行了非法操作,将被closures”更好。

这取决于您的业务逻辑,但您可能需要执行以下一项或多项操作。

  • 回滚您的交易
  • logging错误
  • 提醒应用程序的任何用户
  • 重试该操作
  • 重新审视例外

您也可能希望检查,如果exception是您可以在上述之一之前处理的types。

一个关于VB.NETexception处理的好文章是Rajesh VS 在VB.NET中exception处理

我看到很多build议,如果你不知道如何处理它,不要抓住它。 这只是对的 。 你应该捕捉exception,但也许不在这个层面。 使用你的代码作为例子,我会更像这样写:

 Using connection As New SqlConnection("connection string here"), _ sqlCmd As New SqlCommand("do some SQL", connection), _ sqlDa As New SqlDataAdapter(sqlCmd) sqlDa.Fill(dt) End Using 

不仅没有Try / Catch /最后,没有开放或closures。 .Fill()函数被logging为打开连接(如果需要的话),并且使用块将确保它正确closures, 即使抛出exception也是如此

这让您可以自由地在更高层次上捕获exception – 在UI或业务代码中调用查询运行的function,而不是查询本身。 这个更高级别的代码能够更好地决定如何进行,需要进行哪些日志logging,或者向用户显示更好的错误消息。

事实上,正是这种exception情况才能在你的代码中“冒泡”,使它们变得非常有价值。 如果你总是在那里抛出一个exception,那么exception不会在vb的旧的“On Error Goto X”语法之外增加更多的值。

这取决于sql确实是什么。 是什么东西:

  • 用户呢? 也许创build一个帐户或消息 – 那么你需要通知用户有什么问题
  • 该应用程序自然吗? 像清理日志或类似的东西? 这是致命的吗? 应用程序可以继续吗? 是否可以忽略 – 也许重试? pipe理员应该宣布吗?

从这些问题开始,他们通常会回答如何处理例外情况

除非你正在期待这个错误(API说它可能发生),并且可以处理它(如果发生exception,那么显然有一个步骤),那么你可能想要碰撞出大量的噪音 。 这应该在testing/debugging过程中发生,以便在用户看到它之前修正该错误!

当然,正如评论者所指出的, 用户不应该真正看到这些噪音 。 一个高级的try/catch或其他方法(EMLAH,我听说.net web项目)可以用来向用户显示一个很好的错误信息(“糟糕!出错了!你到底想干什么? “)提交button…

所以基本上,我的观点是: 不要发现你不知道如何处理的错误! (除了高级处理程序)。 提早尽早并尽可能多地提供信息。 这意味着您应该尽可能地logging调用堆栈和其他重要信息。

如果不知道如何应对,不要理会这个例外。

赶上它,而不是在你有可能处理它的地方,你知道如何继续执行之后。

有一件事要记住,在你觉得你想要使用try / catch的部分,你应该把你的Dim语句移出try块。 你可以在块内赋值,但是如果你在try块中定义它们,你将无法访问catch部分的variables,因为它们在这个范围之外。

catch块中的标准做法,包括尝试修复错误,如果可能的话,就是写出我正在使用的任何日志logging机制信息,这些信息是关于导致错误的部分中涉及的关键variables。 这不是必须的,但我发现它通常有助于debugging问题。

我想build议你,如果你不知道如何处理exception,不要抓住它。 编码器通常会捕获exception,并将其全部吞下。

 catch (Exception ex) { /* I don't know what to do.. *gulp!* */ } 

显然这不好,因为坏事正在发生,而且没有采取任何行动。 只捕获可操作的exception!

这就是说,优雅的error handling非常重要。 不要让你的应用程序崩溃,对吧? 您可能会发现ELMAH对Web应用程序很有用,并且全局exception处理程序可以很容易地设置为WinForms或XAML桌面应用程序。

综合起来,您可能会发现这个策略很有用:1.捕获您可能发生的特定exception(DivideByZeroException,SQLException等),并避开通用的catch-allexception; 2.处理完毕后重新抛出exception。 例如

 catch (SQLException ex) { /* TODO: Log the error somewhere other than the database... */ throw; // Rethrow while preserving the stack trace. } 

你真的可以用SQLException做什么? 数据库连接消失了吗? 这是一个错误的查询? 你可能不想添加所有的处理逻辑,除此之外,如果这是你没有想到的东西? 所以,如果可以的话,只要处理这个exception,除非你确定已经解决了,否则重新提高它,并且在全局层面上优雅地处理它(例如,显示一个消息,比如“出错了,但是你可以继续工作。 info:'[ex.Message]'。Abort or Retry?“)

HTH!

约翰·桑德斯,感谢您的纠正。

首先,如果你的应用程序没有办法处理这个exception,那么你不应该首先捕获它( 可以通过exception事件处理程序来完成日志logging,而不需要捕获 )。

如果有什么可以做的话就这样做。 例如,回滚事务并向用户报告失败。 这将取决于您的应用程序。

仅供参考,您不必使用捕获来最终发表声明。

有时候,人们会抛出一个新的exception,并将原来的exception添加为内部exception。

通常用于将错误logging到文件或发送电子邮件给操作员。

有时候,特别是对于SQL来说,这可能意味着一个重复的键,例如,请select另一个用户名,那个用户名已经被占用 – 这一切都归功于您的应用程序。

我会考虑loggingexception发生,并通知用户,您无法完成他们的请求。 这假定这个SQL请求是完成用户试图执行的操作所必需的。

这完全取决于上下文。 可能的选项包括“使用默认数据而不是数据库中的数据”和“向用户显示错误消息”。

如果你不想用它做任何事情,你总是可以尝试/最后而不是尝试/抓住/最后

根据应用程序的types,可以考虑使用全局日志处理程序(即ASP.NET应用程序的“Application_Error”),也可以使用预先构build的开源或MSFT提供的exception处理框架。

作为Enterprise Library 5.0的一部分的exception处理应用程序块是一个build议使用的框架。

除了日志以外,我同意,除非你需要对它们做一些有意义的事情,否则不需要明确地捕捉exception。 而最糟糕的错误就是“捕捉”,然后“扔”,因为这将StackTrace混乱了。

那么,这主要取决于你是否从你的应用程序赚钱。 根据我的经验,没有人(谁支付申请)喜欢看到它崩溃和closures,而不是他们喜欢一个简短的解释性消息有关的错误和第二次机会继续他们正在做什么加上一个机会保存/出口他们的修改数据。 海事组织的一个最佳做法是捕捉一切可能导致错误的东西,如I / O操作,联网相关任务等,并向用户显示相关消息。 如果由于逻辑相关的错误而抛出exception,最好不要抓住它,因为这将帮助你find并纠正实际的错误。

希望这可以帮助。