如何在ruby / rails中合并两个列表并删除重复项?
我有一个源对象在哪里
class Source def ==(other) return false if self.url == nil || other == nil self.url == other.url end
我有以下内容:
def self.merge_internal_and_external_sources(sources=[], external_sources=[]) (sources + external_sources).uniq end
我想合并这两个列表,如果它们已存在于源列表中,则开始从external_sources中踢出项目。 我不确定如何雄辩地做到这一点?
我也尝试过:
sources | external_sources
但由于我的==比较想要在内部比较’url’属性,这会产生一个没有重复删除的结果? 例如:
[src1] == [src2] # true list = [src1] | [src2] list.size # 2
我不确定“merge”是什么#merge
(数组上没有#merge
方法,只有哈希),但你可以这样简化你的代码:
merged = sources | external_sources
要使它适用于您的类,您还需要两个方法: #hash
(实例哈希值,用于初步相等筛选)和#eql?
,用于确认平等:
class Source def hash url.hash + 1 end # Or delegate it to the url: # require 'active_support/core_ext/module/delegation' # delegate :hash, to: :url def eql? other return false if url.nil? || other.url.nil? url == other.url end end
#hash
和#eql?
是每个class级应该具备的基本设施。 添加这些后, #|
和#&
方法将开始在Source
实例的数组上运行。
另一种选择是使用#uniq
方法。 但是,对于裸#uniq
,同样的警告适用于#|
方法: #hash
和#eql?
按顺序用于测试相同的元素。
但是, uniq
可以占用一块 ,所以
(sources + external_sources).uniq &:url
即使懒惰定义#hash
和#eql?
也可以应用#eql?
有关课程的方法。