我有一个汽车品牌列表
makes = [acura, honda, ford]
我正在尝试遍历一个字符串数组,并找出单个字符串是否包含其中一个 make AND 如果是,则将该特定 make 放入数组中
所以我有
strings.each do |string|
if string.include?(*makes)
else
end
end
如何使用 splat 进程的当前参数来确定哪个使与字符串匹配?有没有办法做到这一点?
编辑:正如我在下面的评论中发布的那样,我正在寻找要返回的特定品牌,而不是真/假答案。所以如果字符串是"新丰田赛利卡",则返回应该是"丰田"。
使用 Enumerable#any?
:
makes = ['acura', 'honda', 'ford']
strings = ['hyundai acura ford', 'sports car']
strings.each do |string|
p makes.any? { |make| string.include? make }
end
使用正则表达式的替代方法:(请参阅Regexp::union
)
strings = ['hyundai acura ford', 'sports car']
makes = ['acura', 'honda', 'ford']
pattern = Regexp.union(makes)
strings.each do |string|
p string.match(pattern) != nil
end
更新
strings.each do |string|
p makes.find { |make| string.include? make }
end
或
strings.each do |string|
p makes.select { |make| string.include? make }
end
如果你的makes
不是很长,那么最短的事情之一就是使用正则表达式,如前所述:
makes = ['acura', 'honda', 'ford']
strings = ['hyundai acura ford', 'sports car']
strings.grep(/#{makes.join('|')}/)
# => ["hyundai acura ford"]
经过轻微的讨论,我们认为这是最好的选择之一:
strings.grep(Regexp.union(makes))
另一种方式,通过交叉数组:
makes = ["acura", "honda", "ford"]
strings = [
"I own a Toyota and a Ford",
"My friend Becky loves her Acura",
"I plan to buy a BMW",
"I now have an Acura, but have had both a honda and a Ford"
]
strings.each do |s|
a = s.scan(/(w+)/).flatten.map(&:downcase) & makes
puts "#{s}n" + (a.empty? ? " No matches" : " Matches: #{a.join}")
end
I own a Toyota and a Ford
Matches: ford
My friend Becky loves her Acura
Matches: acura
I plan to buy a BMW
No matches
I now have an Acura, but have had both a honda and a Ford
Matches: acura honda ford
请注意,有必要将scan
与正则表达式一起使用,而不是split
,因为标点符号将是后者的问题(例如,"Acura"将不匹配)。