SQL Server 任意列集中的子字符串匹配

6xfqseft  于 2023-01-20  发布在  其他
关注(0)|答案(1)|浏览(118)

我有一个SQL Server表,其中大约有10列包含各种标识符,包括字母数字和数字。我正在编写一个过程,允许在这些列的任意子集上执行子字符串匹配。例如,“列B中的值包含子字符串bSub,列D中的值包含子字符串dSub,列G中的值包含子字符串gSub”。
下面的代码可以工作,但是非常慢:

SELECT * FROM Table T
WHERE
  (@aSub IS NULL OR T.A LIKE CONCAT('%', @aSub, '%')) AND
  (@bSub IS NULL OR T.B LIKE CONCAT('%', @bSub, '%')) AND
  ...
  (@jSub IS NULL OR T.J LIKE CONCAT('%', @jSub, '%'))

有没有其他的方法来构造这个查询会更好呢?或者有没有什么技术来加快速度呢?我相信索引不会有帮助,因为子字符串匹配LIKE('%...)。

dced5bon

dced5bon1#

一般来说,像这样的字符串匹配总是比较慢的。尽管如此,你可以尝试以下几种方法:
1.将LIKE更改为CHARINDEX,因为实际上并不匹配模式,所以我怀疑charindex的性能更高一些
1.不要检查OR @a IS NULL等,而是从实际不为NULL的参数动态构建查询。

declare @sql = 'select .... WHERE 1 = 1'
if @a is not null
 set @sql = @sql + ' and CHARINDEX(@a, a) > 0'

if @b is not null
 set @sql = @sql + ' and CHARINDEX(@b, b) > 0'

...
exec SP_EXECUTESQL @sql N@a nvarchar(100)', @a = @a, @b = @b...

这将仅检查相关列。
1.为所有或“大多数”搜索到的列创建特定索引,并包含其他所需的列。这可能会有帮助,也可能没有帮助,但如果幸运的话,您可以避免完整聚集索引扫描,因为要遍历的数据比特定列多得多。这一步有点棘手,如果SQL Server决定无论如何都要扫描聚集索引,则可能没有帮助。

相关问题