rails 3 sqlite 通过占位符在查询中传递数组

Posted

技术标签:

【中文标题】rails 3 sqlite 通过占位符在查询中传递数组【英文标题】:rails 3 sqlite pass array in query via placeholder 【发布时间】:2013-12-19 18:07:10 【问题描述】:

我怎样才能将数组作为占位符而不用 sqlite 将其视为 1 个值但数组中有多个值

value = Array.new    

value.push(broadcast_date_from)       
value.push(broadcast_date_to)    

puts value  #["a", "2006-01-02 00:00", "2006-01-02 23:59"]     

find(:all, :order => 'broadcast_date', :conditions => ['name LIKE ? and broadcast_date >= ? and  broadcast_date <= ?', name, @value ])

但我得到这个错误:

 wrong number of bind variables (1 for 3) in: name LIKE ? and broadcast_date >= ? and broadcast_date <= ?   

有没有办法让它在数组中看到 3 个值而不是 1 个。

【问题讨论】:

【参考方案1】:

在调用数组之前,您需要添加 splat 运算符 *

values = ['condition for name']
values.push(broadcast_date_from)       
values.push(broadcast_date_to)

find(:all, :order => 'broadcast_date', :conditions => ['name LIKE ? and broadcast_date >= ? and  broadcast_date <= ?', *values ])

关于splat运算符的小文章:http://theplana.wordpress.com/2007/03/03/ruby-idioms-the-splat-operator/


为您改进:使用.where() 而不是.find()

首先,关于它的优秀指南:http://guides.rubyonrails.org/active_record_querying.html#conditions

然后,用一个小例子来说明 where 的好处:

class User < ActiveRecord::Base
  def get_posts(options = )
    str_conditions = ['user_id = ?']
    args_conditions = [self.id]
    if options.has_key?(:active)
      str_conditions << 'active = ?'
      args_conditions << options[:active]
    end
    if options.has_key?(:after)
      str_conditions << 'created_at >= ?'
      args_conditions << options[:after]
    end
    if options.has_key?(:limit)
      Post.find(:conditions => [str_conditions.join(' OR '), *args_conditions], :limit => options[:limit])
    else
      Post.find(:conditions => [str_conditions.join(' OR '), *args_conditions])        
    end
  end

不同的用法:

user = User.first
user.get_posts(:active => true, :after => Date.today, :limit => 10)
user.get_posts

同样的方法,但是使用 where 方法(非常适合链式作用域):

def get_posts(options = )
  scope = self.posts
  scope = scope.where(active: options[:active]) if options.has_key?(:active)
  scope = scope.where('created_at >= ?', options[:after]) if options.has_key?(:after)
  scope = scope.limit(options[:limit]) if options.has_key?(:limit)

  return scope
end

请记住,您可以使用.where 方法chain scope

User.where(active: true).where('created_at < ?', Date.today-1.weeks).includes(:posts).where(posts:  name: "Name of a specific post" )

【讨论】:

啊,谢谢@mamesaye,但如果我能给你一个提示,请使用.where 方法从数据库中查找对象,它在各个方面都好得多。如果您需要,我可以提供一些使用示例 我刚刚更新了我的答案@mamesaye -- 希望对您有所帮助;;)

以上是关于rails 3 sqlite 通过占位符在查询中传递数组的主要内容,如果未能解决你的问题,请参考以下文章

如何通过 Spring 占位符在 yaml 中表达对象列表或数组?

UITextField 占位符在点击时一直显示

HTML5 占位符在焦点上消失

SQL 语句在Java中如何使用占位符?

当输入和占位符具有不同的字体大小时,输入的占位符在 Chrome 中未对齐

占位符怎么设置