帮我解决这个问题

时间:2011-04-23 08:43:35

标签: sql ruby-on-rails ruby search

我的用户表包含first_namelast_name列,name是虚拟属性。例如,我有这些记录:

Aen Tan
Lily Chou Chou
Nuon Baby

当我用两个单词搜索时,我得到了预期的结果:

"aen tan" Aen Tan
"lily chou" Lily Chou Chou

但是当我用一个词搜索时,例如“aen”我得到了所有三条记录。

这是我的疑问:

scope :find_by_name, lambda {|name| where("first_name LIKE ? or last_name LIKE ?",  '%' + name.split(' ').first + '%', '%' + name.split(' ')[1, name.split(' ').length-1].join(' ') + '%')}

当我用一个单词“aen”搜索时,它产生了这个SQL:

SELECT `users`.* FROM `users` WHERE (first_name LIKE '%aen%' or last_name LIKE '%%')

我认为问题在于姓氏是空的。对此有什么好处?如果只给出一个单词,我应该使用单词?

搜索两个列

这让我想到了我正在思考的其他事情。如果我搜索“tan + aen”,我什么也得不到,但绝对有可能用户会得到颠倒的名字顺序。如何考虑将此考虑在内的查询?

3 个答案:

答案 0 :(得分:1)

你可以将范围作为这样的函数来做。这假设名称只有2个单词。

def self.find_by_name(name)
  names = split(' ')
  if names.size == 1
    YourModel.where("first_name LIKE ?", "%#{names.first}%")
  else
    YourModel.where("first_name LIKE ? AND last_name LIKE ?", "%#{names.first}%")
  end
end

更好的解决方法是拥有一个可以搜索的full_name表属性。在模型创建之后,这很容易构建。

然后你的范围就是:

scope :find_by_name, {|name| where("full_name LIKE ?", "%#{name}%")}

答案 1 :(得分:0)

你可以:

  • 如果查询搜索中没有第二个字,则不在last_name中搜索
  • 将您的条件置于AND条件而不是OR。我猜你会搜索的用户名字 AND 与查询匹配的姓氏。

答案 2 :(得分:0)

SELECT users.* FROM users WHERE (first_name LIKE '%Aen%' And last_name LIKE '%%')

我认为这是解决方案。我试过了,它给出了你想要的相同结果......希望有所帮助