如果一个方法在使用错误的参数调用时死亡或者如果可能的话继续吗?
例如:
my $n = Something->new( retries => 'hello' );
但是retries
会期望一个整数。
答案 0 :(得分:3)
该方法一旦检测到错误就应该死掉。这有助于立即识别问题。如果你继续,它将跛行并在其他地方死亡,使程序处于不一致状态,这使得难以确定问题的根本原因。
答案 1 :(得分:2)
信不信由你,对此有一个完整的哲学讨论
我总是记得一位老师总是说“一个优化和错误的程序做了什么?很多错误的答案非常快”: - )
我认为如果错误无法恢复,错误必须中断执行。在这种情况下,这是输入数据。您只能恢复错误的输入数据,提供有效的默认输入数据,这不是解决问题,而是对其进行篡改。
所以我认为它应该死了。
答案 2 :(得分:2)
取决于。
如果可以将错误的值强制转换为有效值,则可能值得这样做,特别是如果这有助于向后兼容。例如,假设您的Something
类曾被硬编码为重试0次或3次(因此retries
参数是布尔值),但随后您重写了它以接受整数参数。然后你可能想尝试继续接受布尔值......
Something->new(retries => ""); # not an integer, but accept as 0
Something->new(retries => undef); # not an integer, but accept as 0
Something->new(retries => 4); # an integer, accept as 4
Something->new(retries => "Hello"); # not an integer, accept as 3
Something->new(retries => "World"); # not an integer, accept as 3
Something->new(retries => 1); # ambiguous!! probably accept as 1
如果有人给你3.00000105作为参数,你可能只想将其舍入为3.也许他们根据一些复杂的浮点计算计算了理想的重试次数,并且存在舍入误差。你知道他们的意思。
在其他情况下,死亡通常比通过其他机制指示错误条件(设置错误标志,返回false等)更好。
答案 3 :(得分:2)
我会说这取决于错误的性质。虽然模块不是决定是否可以恢复任何给定错误,但最好还是死掉并让调用代码使用eval
(或更好,Try::Tiny
)来恢复。我主要复制内置函数的行为,如果调用不正确,则会死掉,但如果因外部问题而出现错误则返回失败状态。
根据传递的参数提供默认行为会很有用,但如果根本没有意义,则永远不要忽略参数。如果不可能做任何明智的事情,那么应该Carp
,而不是死亡,它会从调用代码的上下文中报告错误。
答案 4 :(得分:2)
这取决于。它归结为情境成本效益分析。要分析成本,我们需要问
在您给出的示例中,不正确的值几乎没有后果,用户将收到警告。无需验证。验证的最佳替代方法是创建一个安全失败的接口,这就是你在这里所拥有的。
避免验证的最常见后果是警告和异常似乎来自代码,而代码是验证代码而不是调用代码。所以对我来说一个非常重要的因素是:
既然有后果,你可能会问为什么要避免验证?有一个很好的理由:它需要更多的代码。
如果您决定添加验证,我会在警告或异常中出现错误结果,而不会返回错误。