0

我需要检查一个对象是否响应任意数量的方法。

我厌倦了这样做:

if a.respond_to?(:foo) && a.respond_to?(:bar) && a.respond_to?(:blah)

什么是更“正确”的 DRY 方式来做到这一点?

4

4 回答 4

3

您始终可以将其包装在辅助方法中:

def has_methods?(obj, *methods)
   methods.all?{|method| obj.respond_to? method}
end
于 2012-11-30T23:05:06.760 回答
2

如果你对猴子补丁没有任何意见,试试这个:

class Object
  def respond_to_all? *meths
    meths.all? { |m| self.respond_to?(m) }
  end

  def respond_to_any? *meths
    meths.any? { |m| self.respond_to?(m) }
  end
end

p 'a'.respond_to_all? :upcase, :downcase, :capitalize
#=> true

p 'a'.respond_to_all? :upcase, :downcase, :blah
#=> false

p 'a'.respond_to_any? :upcase, :downcase, :blah
#=> true

p 'a'.respond_to_any? :upcaze, :downcaze, :blah
#=> false

更新:使用meths.all?meths.any?。@MarkThomas,感谢您提神醒脑。

更新:修正responsd错字。

于 2012-11-30T23:07:22.750 回答
0

检查来自 的Active Support扩展名Rails。它有方法try。由于缺乏上下文,很难说如何使用这种方法,可能是这样的:

if a.try(:foo) && a.try(:bar) && a.try(:blah)

为了使用这种方法,你应该

require 'active_support/core_ext/object/try.rb'

还要检查我的这个方法的版本tryit

于 2012-11-30T23:04:33.753 回答
0

“正确”的方式(或其中一种方式,无论如何)是告诉不要询问,这意味着如果您向对象发送消息,您希望它响应而不会抱怨。这也被称为鸭子打字(如果它会嘎嘎叫,那就是鸭子)。

我不能给你任何具体的建议,因为你还没有提出具体的问题。如果您正在测试三种不同的方法,您似乎不知道对象a是什么类型,这可能是一个有趣的案例。发布更多代码!

于 2012-11-30T23:04:53.277 回答