def fruits_of_kind(kind)
return nil if kind.nil?
result = []
([] << kind).flatten.each{|k| result << basket.select{|f| f.fruit_type == k.to_s }}
result
end
Оператор 'splat', вероятно, является наилучшим способом, но есть две вещи, на которые следует обратить внимание: передача nil или списков. Чтобы изменить решение Песто для ввода / вывода, который вам нужен, вы должны сделать что-то вроде этого:
def fruits_of_kind(*kinds)
return nil if kinds.compact.empty?
basket.select do |fruit|
kinds.flatten.each do |kind|
break true if fruit.fruit_type == kind.to_s
end == true #if no match is found, each returns the whole array, so == true returns false
end
end
Если вы передадите nil, * преобразует его в [nil]. Если вы хотите вернуть nil вместо пустого списка, вы должны сжать его (удалить нули) в [], а затем вернуть nil, если он пуст.
Если вы передадите список, например, [: apple, 'banana'], * преобразует его в [[: apple, 'banana']]. Это небольшая разница, но это список из одного элемента, содержащий другой список, поэтому вам нужно сгладить виды перед выполнением цикла «каждый». Сглаживание преобразует его в [: apple, 'banana'], как вы ожидаете, и даст вам результаты, которые вы ищете.
РЕДАКТИРОВАТЬ : еще лучше, благодаря Грегу Кэмпбеллу:
def fruits_of_kind(basket, kind)
return nil if kind.nil?
kind_list = ([] << kind).flatten.map{|kind| kind.to_s}
basket.select{|fruit| kind_list.include?(fruit) }
end
ИЛИ (используя сплат)
def fruits_of_kind(*kinds)
return nil if kinds.compact.empty?
kind_list = kinds.flatten.map{|kind| kind.to_s}
basket.select{|fruit| kind_list.include?(fruit.fruit_type) }
end