我有一个生成随机输出的函数(字符串)。
我需要调用该函数,直到得到3个不同的输出(字符串)。
通过调用函数生成具有3个唯一字符串的数组的最优雅方法是什么?如果未在指定的尝试次数中生成输出,则限制可以调用函数的次数?
以下是我目前的情况:
output = []
limit_calls = 5
limit_calls.times do |i|
str = generate_output_function
output.push str
break if output.uniq.size > 2
end
这可以美化/缩短为1行吗?我非常肯定在红宝石中......:)
由于
答案 0 :(得分:3)
使用集合可以使(稍微)更容易:
require 'set'
output = Set.new
limit_calls = 5
call_count = 0
while output.size < 3 and call_count < limit_calls
output << generate_output_function
call_count += 1
end
output
或使用数组
output = []
limit_calls = 5
while output.size < limit_calls and output.uniq.size < 3
output << generate_output_function
end
output.uniq
使用呼叫限制更新。好像Array版本获胜!谢谢Iain!
还会使用inject来思考一个版本。
更新2 - 注入:
5.times.inject([]) { |a, el| a.uniq.size < 3 ? a << generate_output_function : a }
有你的oneliner。我不确定我喜欢它因为它有点难以遵循.....
答案 1 :(得分:1)
Froderik的回答错过了call_limit要求。像...这样的函数怎么样?
def unique_string_array(call_limit)
output = []
calls = 0
until (output.size == 3 || calls == call_limit) do
(output << generate_output_function).uniq! && calls+=1
end
output
end
它不是单行,但它是可读的...通过这种实现,你最终可能会得到小于3的数组。最重要的是你有一个测试可以断言你想要的行为! (为了彻底测试这个,你必须将对generate_output_function的调用存根)