Ruby数组交集

使用’&’时,两个包含对象的数组不会返回相交数组之间.
请看下面的代码
ruby-1.9.2-p290 :001 > class A
ruby-1.9.2-p290 :002?>   include Comparable
ruby-1.9.2-p290 :003?>   attr_reader :key
ruby-1.9.2-p290 :004?>   def initialize(key)
ruby-1.9.2-p290 :005?>     @key = key
ruby-1.9.2-p290 :006?>     end
ruby-1.9.2-p290 :007?>   def <=> obj
ruby-1.9.2-p290 :008?>     @key <=> obj.key
ruby-1.9.2-p290 :009?>     end
ruby-1.9.2-p290 :010?>   end
 => nil 
ruby-1.9.2-p290 :011 > class B
ruby-1.9.2-p290 :012?>   attr_reader :key
ruby-1.9.2-p290 :013?>   def initialize(key)
ruby-1.9.2-p290 :014?>     @key = key
ruby-1.9.2-p290 :015?>     end
ruby-1.9.2-p290 :016?>   end
 => nil 
ruby-1.9.2-p290 :017 > A.new(1) == A.new(1)
 => true 
ruby-1.9.2-p290 :019 > B.new(1) == B.new(1)
 => false 
ruby-1.9.2-p290 :020 > a1 = [A.new(1),A.new(2),A.new(3)]
 => [#<A:0x000001009e2f68 @key=1>,#<A:0x000001009e2f40 @key=2>,#<A:0x000001009e2f18 @key=3>] 
ruby-1.9.2-p290 :021 > a2 = [A.new(3),A.new(4),A.new(5)]
 => [#<A:0x000001009d44e0 @key=3>,#<A:0x000001009d44b8 @key=4>,#<A:0x000001009d4490 @key=5>] 
ruby-1.9.2-p290 :023 > a1 | a2
 => [#<A:0x000001009e2f68 @key=1>,#<A:0x000001009e2f18 @key=3>,#<A:0x000001009d44e0 @key=3>,#<A:0x000001009d4490 @key=5>] 
ruby-1.9.2-p290 :024 > a1 & a2
 => []

不应该a1& a2回归:

[#<A:0x000001009e2f18 @key=3>]

或者,我只是遗漏了一些东西……

解决方法

不,你需要为Array#&amp ;;实现哈希等式.和数组#|工作(仅通过正常比较实现它将是O(n * m)).注意数组#|也返回了错误的结果:它包含重复项.

这种等式方法可以这样实现:

def hash
   @key.hash ^ A.hash # just to get a different hash than the key
 end

 alias eql? ==

另外,你的< =>如果另一个对象没有响应#key则失败. ==不应该失败,如果两个对象无法比较,它应该返回false.它也是你不想使用respond_to?的方法之一,而是is_a? :你不希望电影等于一本书,因为它们恰好具有相同的标题.

def <=>(other)
  @key <=> other.key if other.is_a? A
end

相关文章

validates:conclusion,:presence=>true,:inclusion=>{...
一、redis集群搭建redis3.0以前,提供了Sentinel工具来监控各...
分享一下我老师大神的人工智能教程。零基础!通俗易懂!风趣...
上一篇博文 ruby传参之引用类型 里边定义了一个方法名 mo...
一编程与编程语言 什么是编程语言? 能够被计算机所识别的表...
Ruby类和对象Ruby是一种完美的面向对象编程语言。面向对象编...