【问题标题】:Get best hit first首先获得最佳打击
【发布时间】:2022-01-08 03:39:11
【问题描述】:

我有一个表部门,其中包含 SearchKeysName 和 BOLD_ID 列。 Bold_ID 只是用于标识行的数字。 它包含这样的数据:

Bold_ID; SearchKeysName
1005; [12212][FALKENBERG][32-1][][523451]
1000; [124132][AB CD BYGG][GÖTEBORG][124132-1][][CD-BYGG CO][556435979101]

要搜索数据,我有这样的 SQL:

SELECT DISTINCT TOP 100 BOLD_ID FROM Department UPPER(SearchKeysName) LIKE '%\[%32-1%]%' ESCAPE '\'

在这种情况下,我搜索了 32-1,因此它会选择上面的行。 我想要的是确保准确的命中放在结果之上。 像这样

1000
1005

这当然是一个简化的例子。实际上有数千行,所以我可以错过 32-1 的第一行,因为当搜索字符串很短时还有很多其他行和这个字符串。

到目前为止,我唯一的想法是进行 2 次搜索。 一个与

LIKE '%\[32-1]%'

如果没有找到任何东西,请尝试像上面那样更通用。

编辑 现在试试这个:

SELECT distinct TOP 100 DEPARTMENT.BOLD_ID
from Department 
where upper(SearchKeysName) like '%\[%32-1%]%' ESCAPE '\'
order by case when SearchKeysName like '%\[32-1]%' ESCAPE '\' then 0 else 1 end

得到了这个

Msg 145, Level 15, State 1, Line 1
ORDER BY items must appear in the select list if SELECT DISTINCT is specified.

【问题讨论】:

  • 看来您的问题实际上在于将多个原子数据元素组合在一个列中。您可能需要两个联合查询。
  • 是的,这不是我的设计。但我想能够一次搜索很多东西是一种妥协。
  • 您要搜索的值是否始终位于“段”的末尾,或者类似[432-123] 之类的可能吗?
  • 单列中的分隔数据几乎总是错误的架构设计。这需要一张额外的桌子。
  • 是的,我知道这个设计很丑。它是很久以前完成的,团队中没有人敢于更改它,因为它运行得很好。关于 [432-123]。这是可能的,但不太可能。在减号之后通常只有 1 或 2 个数字

标签: sql sql-server-2012


【解决方案1】:

使用case 表达式首先获得准确的命中行:

order by case when SearchKeysName like '%\[32-1]%' ESCAPE '\' then 0 else 1 end, Bold_ID

要获得不同的 BOLD_ID,请执行 GROUP BY,首先对完全匹配的 BOLD_ID 进行排序(即使它也有非完全匹配):

SELECT TOP 100 BOLD_ID
from Department 
where SearchKeysName like '%\[%32-1%]%' ESCAPE '\'
group by BOLD_ID
order by min(case when SearchKeysName like '%\[32-1]%' ESCAPE '\' then 0 else 1 end),
         BOLD_ID

【讨论】:

  • 啊,你是我的英雄! :)
猜你喜欢
  • 2021-03-08
  • 1970-01-01
  • 1970-01-01
  • 2011-10-29
  • 2018-07-19
  • 1970-01-01
  • 1970-01-01
  • 2018-03-13
  • 1970-01-01
相关资源
最近更新 更多