我发现自己在Ruby中使用类似PHP的循环,当语言的其余部分如此整洁时,感觉不对。我结束了这样的代码:
conditions_string = ''
zips.each_with_index do |zip, i|
conditions_string << ' OR ' if i > 0
conditions_string << "npa = ?"
end
# Now I can do something with conditions string
我觉得我应该可以做这样的事情
conditions_string = zips.each_with_index do |zip, i|
<< ' OR ' if i > 0
<< "npa = ?"
end
在Ruby中使用块设置变量是否有'整洁'的方式?
答案 0 :(得分:4)
我想到的第一件事是:
a = %w{array of strings} => ["array", "of", "strings"]
a.inject { |m,s| m + ' OR ' + s } => "array OR of OR strings"
但这可以通过
来完成a.join ' OR '
虽然我认为你很快就需要这个结构,但是为了复制你的确切例子,我可能会使用:
([' npa = ? '] * a.size).join 'OR'
答案 1 :(得分:4)
由于你实际上没有使用zip的值,我建议
zips.map {|zip| "npa = ?" }.join(" OR ")
但总的来说,我建议查看Enumerable#inject函数来避免这种循环。
答案 2 :(得分:1)
您似乎没有在循环中访问zip
,因此以下内容应该有效:
conditions_string = (['npa = ?'] * zips.length).join(' OR ')
如果您需要访问zip
,则可以使用:
conditions_string = zips.collect {|zip| 'npa = ?'}.join(' OR ')
答案 3 :(得分:1)
虽然其他人已经为您的特定问题提供了更多惯用解决方案,但实际上有一种很酷的方法Object#instance_eval
,这是许多Ruby DSL使用的标准技巧。它将self
设置为其块内instance_eval
的接收者:
简短的例子:
x = ''
x.instance_eval do
for word in %w(this is a list of words)
self << word # This means ``x << word''
end
end
p x
# => "thisisalistofwords"
它并不像Perl $_
那样普遍覆盖所有内容,但它允许您隐式地将方法发送到一个对象。
答案 4 :(得分:0)
在1.8.7+中,您可以使用each_with_object
它取代了DigitalRoss的'注入'习语:
a = %w{hello my friend} => ["hello", "my", "friend"]
a.each_with_object("") { |v, o| o << v << " NOT " } => "hello NOT my NOT friend NOT"