Gab*_*esy 17 ruby equality date
今天写一些rspec时,我遇到了一些意外行为,将Date(和Time)实例与nil进行比较.这是使用原始ruby(没有Rails或其他库)的示例:
user@MacBook-Work ~ $ ruby -v
ruby 1.8.7 (2008-08-11 patchlevel 72) [universal-darwin10.0]
user@MacBook-Work ~ $ irb
>> 1 == nil
=> false
>> "string" == nil
=> false
>> :sym == nil
=> false
>> false == nil
=> false
>> [] == nil
=> false
>> {} == nil
=> false
>> Proc.new {} == nil
=> false
Run Code Online (Sandbox Code Playgroud)
到目前为止,这么好,对吗?
>> Date.new == nil
=> nil
>> Time.new == nil
=> nil
Run Code Online (Sandbox Code Playgroud)
Date确实实现了自己的===,这很好用:
>> Date.new === nil
=> false
Run Code Online (Sandbox Code Playgroud)
有没有解释为什么会发生这种情况或为什么这是理想的行为?==似乎是从Comparable实现的.==,但是关于它的文档没有任何迹象表明它会返回nil.对此有何设计决定?
更新!1.9.2中的情况并非如此:
$ irb
ruby-1.9.2-p136 :001 > require 'date'
=> true
ruby-1.9.2-p136 :002 > Date.new == nil
=> false
ruby-1.9.2-p136 :003 > Time.new == nil
=> false
Run Code Online (Sandbox Code Playgroud)
sep*_*p2k 12
我检查了源代码,这是我发现的:
Comparable定义的比较运算符都与函数rb_cmpint一起使用<=>.rb_cmpint当其中一个操作数为零时引发异常.
因此,如果rhs与lhs不具有可比性,则Comparable的运算符会引发异常.即5 < 2是假的,但5 < "la"引发了一个例外.他们这样做是为了区分<因为rhs较小而不适用的情况以及由于rhs不具有可比性而不适用的情况.或者换句话说:什么时候x < y是假的,暗示这x >= y是真的.因此,如果不是这种情况,它会引发异常.
==提出异常会很糟糕,因为==通常不会(也不应该)要求其操作数具有可比性.但是==使用与其他操作数相同的方法,这会引发异常.所以整个功能简单地包裹在一个rb_rescue.nil如果抛出异常,则返回.
请注意,这仅适用于ruby 1.8.这已在1.9中修复,现在==永远不会返回nil(当然,如果您定义自己的==那个).
如果您依赖于此代码,您可以随时使用.nil?任何Ruby对象响应的方法.
>> Date.new.nil?
=> false
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
3604 次 |
| 最近记录: |