我有以下变量:
query = "(first_name = ?) AND (country = ?)" # string
values = ['Bob', 'USA'] # array
我需要以下结果:
result = "(first_name = Bob) AND (country = USA)" # string
替换次数各不相同(1..20)。
在Ruby中执行此操作的最佳方法是什么?
答案 0 :(得分:3)
如果你不介意破坏阵列:
query.gsub('?') { values.shift }
否则只需复制数组然后进行替换。
已编辑:使用gsub('?')代替正则表达式。
答案 1 :(得分:2)
如果您可以控制query
字符串,则String#%运算符就是您所需要的:
query = "(first_name = %s) AND (country = %s)" # string
values = ['Bob', 'USA'] # array
result = query % values
#=> "(first_name = Bob) AND (country = USA)"
您必须在?
字符串中将%s
替换为query
。
答案 2 :(得分:1)
query = "(first_name = ?) AND (country = ?)"
values = ['Bob', 'USA']
result = query.dup
values.each{|s| result.sub!("?",s) }
p query
# >> "(first_name = Bob) AND (country = USA)"
答案 3 :(得分:1)
values.inject(query){|s1, s2| s1.sub("?", s2)}
答案 4 :(得分:0)
由于此问题已标记为ruby-on-rails,因此您可以(应该)将ActiveRecord::QueryMethods#where
与Array Conditions一起使用。
如果您在values
中提供错误数量的绑定变量,则会引发ActiveRecord::PreparedStatementInvalid
,这样您就无法自行检查。
这不仅是优雅的,因为Rails会为您执行替换,它还可以通过在此过程中清理SQL来帮助您防范SQL injection attacks。
假设您的模型被调用User
并且query
和value
与您的问题相同,那么:
User.where(query, *values)
...将生成SQL,如:
SELECT * FROM users WHERE first_name = 'Bob' AND country = 'USA';
上面的示例将执行查询。要在不执行的情况下显示生成的SQL,只需调用ActiveRecord::Relation#to_sql
:
User.where(query, *values).to_sql