【问题标题】:Handle default exception in ruby处理 ruby​​ 中的默认异常
【发布时间】:2013-07-06 13:23:33
【问题描述】:

如何实现异常的默认行为? begin rescue else 不起作用(我认为应该)。

而且,else 在场景中不是毫无意义吗?在没有引发异常时必须运行的任何代码都会在 begin-rescue 块之间运行。

顺便说一下,我有以下解决方法,但我对此并不满意。

class MyException < Exception
end

class YourException < Exception
end

begin
  raise MyException if 2 > 50
  raise YourException if 1 < 90
rescue Exception => e
  case e.message
  when /MyException/
    puts "MyException Caught"
  else
    puts "Default Exception Caught"
  end
end

【问题讨论】:

  • 应该做以下事情:rescue MyException,然后是rescue Exception(不知道为什么我之前没有这样做。:()

标签: ruby exception


【解决方案1】:

首先,你真的不应该继承Exception。它是所有 Ruby异常的超类,包括NoMemoryErrorSyntaxErrorInterruptSystemExit;所有这些你通常不需要解救。不鼓励这样做,无论是意外还是故意,因为它会阻止程序正确退出,即使它被用户中断。它还可以隐藏或产生一些非常隐蔽的错误。

您想要子类化的是StandardError,它是我们在日常编程中看到的大多数 Ruby 错误的超类。如果你不指定一个,这个类也是rescued:

begin
  object.do_something!
rescue => error    # will rescue StandardError and all subclasses
  $stderr.puts error.message
end

我相信这是您正在寻找的“默认行为”。您可以处理特定错误,然后处理所有其他错误:

class CustomApplicationError < StandardError
end

begin
  object.do_something!
rescue CustomApplicationError => error
  recover_from error
rescue => error
  log.error error.message
  raise
end

else 子句在错误处理中并非毫无意义。当且仅当没有引发异常时,它将执行嵌套代码,而不是 ensure 子句,无论如何都会执行代码。它允许您处理成功 案例。

begin
  object.do_something!
rescue => error
  log.error error.message
else
  log.info 'Everything went smoothly'
end

【讨论】:

  • else 子句对我来说意义不大,因为我一直在思考如何处理默认异常情况。一旦我得到它, else 就有意义了。感谢您的回复。 :)
  • 想通了。您的第二个代码块是有意义的。不要救援“异常”,而只是将救援用于其他异常。谢谢:)
【解决方案2】:

首先,我不明白您为什么要对错误消息进行大小写处理。为什么不通过他们的班级来处理错误本身呢?然后,它会是这样的:

begin
  raise MyException if 2 > 50
  raise YourException if 1 < 90
rescue Exception => e
  case e
  when MyException
    puts "MyException Caught"
  else
    puts "Default Exception Caught"
  end
end

其次,像上面那样做并不是直接的方法。正确的做法是:

begin
  raise MyException if 2 > 50
  raise YourException if 1 < 90
rescue MyException
  puts "MyException Caught"
rescue Exception
  puts "Default Exception Caught"
end

如果YourExceptionStandardError 的子类,那么它可以被rescue 捕获而无需指定异常类。

【讨论】:

  • 是的,这是正确的答案,我后来想通了(如评论中所述)。不过谢谢。 :)
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2017-08-20
  • 2016-06-05
  • 1970-01-01
  • 1970-01-01
  • 2015-12-29
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多