SQL Server带更新的最佳匹配查询(T-SQL)
我试图找出实现以下目标的最佳SQL查询 我有一个包含ZipCodes/PostalCodes的表,让我们假设以下结构:SQL Server带更新的最佳匹配查询(T-SQL),sql,sql-server,tsql,Sql,Sql Server,Tsql,我试图找出实现以下目标的最佳SQL查询 我有一个包含ZipCodes/PostalCodes的表,让我们假设以下结构: #tmpTable ------------------------------------------------------------------------------------ ID | user1_enteredzip | user1_bestmatchzip | user2_enteredzip | user2_bestmatchzip | ----------
#tmpTable
------------------------------------------------------------------------------------
ID | user1_enteredzip | user1_bestmatchzip | user2_enteredzip | user2_bestmatchzip |
------------------------------------------------------------------------------------
1 | 12 | *1234* | 4567 | **456** |
2 |
3 |
4 |
表2:U代码:
ID | ZipCode
---------------
1 1234
2 1235
3 456
等等
我的应用程序的用户填写一个配置文件,要求他们输入ZipCode(PostalCode)。
假设有时,用户会输入我的表中未定义的ZipCode,我将尝试根据用户输入的zip建议最佳匹配
我正在使用以下查询:
Declare @entered_zipcode varchar(10)
set @entered_zipcode = '23456'
SELECT TOP 1 table_codes.ZipCode
FROM table_codes
where @entered_zipcode LIKE table_codes.ZipCode + '%'
or table_codes.ZipCode + '%' like @entered_zipcode + '%'
ORDER BY table_codes.ZipCode, LEN(table_codes.ZipCode) DESC
基本上,我正在尝试以下方法:
- 如果@entered_zipcode比表中的任何邮政编码都长,我将尝试在zip表中获得与@entered_zipcode匹配的最佳前缀
- 如果@entered_zipcode比表中的任何现有代码都短,我将尝试将其用作前缀,并在表中获得最佳匹配
#tmpTable
------------------------------------------------------------------------------------
ID | user1_enteredzip | user1_bestmatchzip | user2_enteredzip | user2_bestmatchzip |
------------------------------------------------------------------------------------
1 | 12 | *1234* | 4567 | **456** |
2 |
3 |
4 |
输入的邮政编码是用户输入的邮政编码,介于*.*之间是我的查找表中的最佳匹配代码,我正在使用下面的查询尝试获取该代码
查询似乎需要一点时间,这就是我请求帮助优化它的原因:
update #tmpTable
set user1_bestmatchzip = ( SELECT TOP 1
zipcode
FROM table_codes
where #tmpTable.user1_enteredzip LIKE table_codes.zipcode + '%'
or table_codes.zipcode + '%' like #tmpTable.user1_enteredzip + '%'
ORDER BY table_codes.zipcode, LEN(table_codes.zipcode) DESC
),
user2_bestmatchzip = ( SELECT TOP 1
zipcode
FROM table_codes
where #tmpTable.user2_enteredzip LIKE table_codes.zipcode + '%'
or table_codes.zipcode + '%' like #tmpTable.user2_enteredzip + '%'
ORDER BY table_codes.zipcode, LEN(table_codes.zipcode) DESC
)
from #tmpTable
如果将临时表更改为:
id | user | enteredzip | bestmatchzip
10 | 1 | 12345 | 12345
20 | 2 | 12 | 12345
即:使用列保存用户编号(1或2)。这样,您将一次更新一行
另外,orderby
需要时间,您是否在zipcode上设置了索引?您不能在zipcodes表中创建一个字段“length”来预计算zipcodes lenghts吗
编辑:
我在想由LEN订购是没有意义的,你可以删除它!如果zipcode不能有重复项,那么按zipcode排序就足够了。如果他们可以,那么
LEN
将始终相等 如果将临时表更改为:
id | user | enteredzip | bestmatchzip
10 | 1 | 12345 | 12345
20 | 2 | 12 | 12345
即:使用列保存用户编号(1或2)。这样,您将一次更新一行
另外,orderby
需要时间,您是否在zipcode上设置了索引?您不能在zipcodes表中创建一个字段“length”来预计算zipcodes lenghts吗
编辑:
我在想由LEN订购是没有意义的,你可以删除它!如果zipcode不能有重复项,那么按zipcode排序就足够了。如果他们可以,那么
LEN
将始终相等 您正在比较两个字符串的第一个字符-如果您比较最小长度的子字符串呢
select top 1 zipcode
from table_zipcodes
where substring(zipcode, 1, case when len(zipcode) > len (@entered_zipcode) then len(@entered_zipcode) else len (zipcode) end)
= substring (@entered_zipcode, 1, case when len(zipcode) > len (@entered_zipcode) then len(@entered_zipcode) else len (zipcode) end)
order by len (zipcode) desc
这将删除或,并允许在@entered_zipcode(如表_codes.zipcode+'%')*)中使用索引*。另外,在我看来,结果的顺序是错误的——先是较短的Zipcode。您正在比较两个字符串的第一个字符——如果您比较最小长度的子字符串呢
select top 1 zipcode
from table_zipcodes
where substring(zipcode, 1, case when len(zipcode) > len (@entered_zipcode) then len(@entered_zipcode) else len (zipcode) end)
= substring (@entered_zipcode, 1, case when len(zipcode) > len (@entered_zipcode) then len(@entered_zipcode) else len (zipcode) end)
order by len (zipcode) desc
这将删除或,并允许在@entered_zipcode(如表_codes.zipcode+'%')*)中使用索引*。另外,在我看来,结果的顺序是错误的——先是较短的Zipcode。为什么要使用临时表?我正在尝试使用临时表进行一些计算。我想展示的是,我需要在一次更新操作中获得两列的最佳匹配zip。在我看来,我的查询不是最理想的方式。为什么要使用临时表?我正在尝试使用临时表进行一些计算。我想展示的是,我需要在一次更新操作中获得两列的最佳匹配zip。在我看来,我的查询并不是最理想的方式。谢谢你。我有一个关于ZipColumn的索引,但是长度字段听起来像是一个很棒的主意。我要试试这个,然后带着结果回来。非常感谢。预先计算的“zip-len”有助于减少执行时间,但没有那么多。我正在考虑你建议的另一种办法。瓦卡尼诺,你真的很好。我没有想到这一点,但你是绝对正确的。由Len订购毫无意义。我刚刚删除了这个条款,现在执行时间缩短了3-4倍。从700毫秒到200毫秒。你太棒了!谢谢你,瓦卡尼诺。我有一个关于ZipColumn的索引,但是长度字段听起来像是一个很棒的主意。我要试试这个,然后带着结果回来。非常感谢。预先计算的“zip-len”有助于减少执行时间,但没有那么多。我正在考虑你建议的另一种办法。瓦卡尼诺,你真的很好。我没有想到这一点,但你是绝对正确的。由Len订购毫无意义。我刚刚删除了这个条款,现在执行时间缩短了3-4倍。从700毫秒到200毫秒。你太棒了!谢谢尼古拉的回答。我也尝试了你的aproach,但是执行时间比我当前的查询要长一倍。(这是我最初的问题,没有Vulkanino建议的ORDER by len条款)谢谢Nikola的回答。我也尝试了你的aproach,但是执行时间比我当前的查询要长一倍。(这是我的原始查询,没有Vulkanino建议的ORDER by len条款)