返回false与在Ruby中引发异常 - 何时以及为何?

时间:2014-05-22 19:01:42

标签: ruby-on-rails ruby exception-handling

我对以下概念感到困惑:

  • 不要将异常用作控制流程
  • 不要将nil / false作为例外返回

说我有以下实例方法:

class Logo
  # This method has some logic to create an image using Rmagick
  def process
    begin
      @logo_image = RmagickHelper.new(self.src)
    rescue Magick::ImageMagickError
      raise Exceptions::LogoUnprocessable, "ImageMagick can't process the URL"
    end
  end
end

因此,在更通用的方法中,我有以下内容:

def build_all_images
    begin
      @logo.process
    rescue Exceptions::LogoUnprocessable
      @logo.status = 'unprocessable'
      return false #This terminates the method so no more stuff is processed, because logo could not be processed.
    end
#....
end

我的问题是:

这是否正确:

raise Exceptions::LogoUnprocessable, "ImageMagick can't process the URL"

或者我应该刚刚完成

return false

2 个答案:

答案 0 :(得分:7)

曾几何时,有一种没有异常构造的语言()。每条消息返回一个整数 - 0表示成功,或者一些错误代码表示失败。如果来电者在继续之前没有检查返回代码 - 他会被搞砸。此外,大多数情况下,呼叫者对失败没有任何帮助,所以即使他确实检查了结果 - 他可能做的唯一聪明的事情就是返回自己的错误代码... < / p>

然后来了,带有异常构造,仅用于这些用例。在方法陷入无法处理的情况下(例如,读取不存在的文件,或在没有网络连接的情况下浏览网页),会出现例外情况。

滥用Exception构造意味着在完全预期的情况下引发异常,例如:

def even?
  if (self % 2 != 0)
    raise NumberNotEvenException
  end
end

这里一个奇怪的数字是合法的,并且是预期的;抛出错误是滥用异常构造。

当方法无法履行承诺时,抛出异常。

另一方面 - 当方法失败时返回nilfalse会让我们回到快乐天,呼叫者注意到失败的负担,并弄清楚出了什么问题 - 不好玩。

答案 1 :(得分:3)

差异与故障发生的频率以及是否是简单的返回值有关。

询问“这是一个有效的网址”会产生“错误”值,但在这种情况下,似乎在预期有效网址时,失败案例需要例外。

例外是“例外”或不寻常。例外情况发生在命令方法中,你告诉它“执行此操作”并说“oops!”

流控制更像是一个问题“这是什么”,在这种情况下,“oops”没有意义。

另外,考虑调用代码的次数 - 异常比简单的返回值花费更多的时间来处理。