首先让我反对@Sravan 发布的解决方案:
虽然猴子修补类是正确的——有时甚至是一个很好的解决方案——但你必须小心如何去做,因为它可能会成为定时炸弹:
Ruby 不断发展,新版本通常会向现有类添加方法。这意味着如果你添加一个方法 Array#search,并且新版本的 Ruby 也会添加一个同名的方法,你的新方法将静默地覆盖 Ruby 中的方法。您可能很长时间都不会注意到它,直到您使用应该使用 Rubys Array#search 的功能 - 也许通过使用 stdlib 中的新功能 - 并且您会得到奇怪的结果。追查此类错误可能是一场噩梦。当您使用 search 作为方法名称时,情况正是如此。
现在,那该怎么做呢?三种可能:
(1) 如果您进行猴子补丁,请至少使用一个不太可能成为官方接口一部分的方法名称。它可能有你的项目名称作为前缀,或者大量的下划线字符,等等。请注意,这不是 100% 万无一失的:Ruby 的更高版本可能会在后台添加一个与您选择的名称完全相同的私有方法,但当然,您的名称越奇怪,发生这种情况的可能性就越小。
(2) 如果您不喜欢这种使用“笨拙”名称的想法,您至少可以在定义新方法之前测试它是否已经存在,如果不存在则抛出异常:
class Array
if self.method_defined?(:search)
raise "#{self.class}::search already defined"
else
def search(...)
...
end
end
end
(3) 第三种可能性是避免猴子修补并将该方法保留在您的 Island 类中。在这种情况下,方法定义会有所不同:
class Island
def self.filter(array, string)
...
end
end
它会被调用
Island.filter(myarray, mystring)
更新:忘记了第四种可能性:
(4) 你可以让 Island 成为 Array 的子类。我不知道您还想对您的岛屿做什么,但也许这是一个值得考虑的选择:
class Island < Array
def filter(string)
...
end
end
当然,在调用filter的时候,你需要把你的数组变成一个孤岛,然后才能使用它:
list = Island.new([....])