7645 Null 或空全文谓词

Posted

技术标签:

【中文标题】7645 Null 或空全文谓词【英文标题】:7645 Null or empty full-text predicate 【发布时间】:2010-09-16 10:16:49 【问题描述】:

我有一个在 SQL2005 上运行良好的查询,但将数据库移动到 SQL2008 时出现标题中的错误。

出现问题的代码是使用空参数调用 CONTAINS、CONTAINSTABLE 或 FREETEXT。但是我试图只在有这样的值时调用或加入

where (@search_term = '' or (FREETEXT(lst.search_text, @search_term)))

left join containstable (listing_search_text, search_text,  @search_term) ftb on l.listing_id = ftb.[key] 
    and len(@search_term) > 0

但是我找不到任何可以在 SQL2008 上运行的解决方法。有什么想法吗?

我知道我可以执行动态 SQL 或使用具有两种不同情况的 if 语句(使用 FT 连接选择,选择不使用 FT 连接。还有不需要这样做的更好的解决方法吗?

【问题讨论】:

【参考方案1】:

我发现如果 SQL-Server 是 configured to ignore "noise words".,则使用“a”作为默认值是可行的

SET @SearchPhrase = coalesce(@SearchPhrase, 'a'); /* replace with 'a' if null parameter */ 
SELECT ... WHERE 
    (@SearchPhrase = 'a' OR contains(Search_Text, @SearchPhrase)) 

【讨论】:

【参考方案2】:

只需添加双引号。 您可以检查空字符串,然后在其中添加双引号。

Set @search_term = case when @search_term = '' then '""' else @Address End

给你-

where (@search_term = '""' or (FREETEXT(lst.search_text, @search_term)))

【讨论】:

【参考方案3】:

我今天在将自己的数据库从 SQL 2005 转换为 SQL 2008 时找到了答案。

"" 传递给您的搜索词并将@search_term = '' 测试更改为@search_term = '""' SQL server 会忽略双引号,不会抛出错误。

例如,以下实际上会返回用户表中的所有记录:

declare  @SearchTerm nvarchar(250)

SET @SearchTerm = '""'

select UserId, U.Description, U.UserName
from dbo.Users U
WHERE ((@SearchTerm = '""') OR CONTAINS( (U.Description, U.UserName), @SearchTerm))

如果您使用的是 .Net,则可以获取 E. W. Bachtal 的 FullTextSearch 类的副本。他的网站信息量很大:http://ewbi.blogs.com/develops/

【讨论】:

(@SearchTerm = '""') 谓词会增加大量读取,并且查询偶尔会超时(如whiplashtony 所述)【参考方案4】:

在 SP2 CU4 中修复了 FTS 和 OR 操作数的问题。如果您处于该级别或更高级别,则 OR 条件应该运行正常而无需 UNION。我们尝试了 SP2 CU8 的最新更新,FTS 现在可以与 OR 一起使用。此外,以前会失败的搜索(例如 3.12)现在工作得很好。

【讨论】:

【参考方案5】:

这个解决方案在 SQL 2008 上对我不起作用。答案似乎很清楚,被认为很有用,但我会在有 2M 记录的表上超时。事实上,它锁定了一个在 SSMS 中运行查询的服务器。

它似乎不喜欢 where 子句中的 OR,但我可以很好地运行查询来分隔条件。

我最终成功地使用了 UNION 作为解决方法。

declare  @SearchTerm nvarchar(250)

SET @SearchTerm = '""'

select UserId, U.Description, U.UserName
from dbo.Users U
WHERE ((@SearchTerm = '""') 

UNION 

select UserId, U.Description, U.UserName
from dbo.Users U
WHERE CONTAINS( (U.Description, U.UserName), @SearchTerm)) 

【讨论】:

您遇到的问题可能是由于我拥有的那个根本没有优化。最近我发现在 WHERE 子句中使用 UNION 代替 OR 的运行速度要快几倍。所以+1 我有一个查询,其中包含大量 LIKE 和前导通配符,它​​们像狗一样奔跑。我试过全文索引,但根本没有帮助。使用 UNIONs 而不是 ORs 使我的查询从大约 15 秒缩短到不到 1 秒。+1!!!! 如果我在两个表之间有一个内部连接并且我想对这两个表进行全文搜索怎么办?这意味着我需要大约 3-4 个工会?

以上是关于7645 Null 或空全文谓词的主要内容,如果未能解决你的问题,请参考以下文章

对于 CONTAINS 全文谓词,SQL Server 2008 中的逻辑短路似乎失败

谓词中的 CASE 中为 NULL

将常量与空集进行比较时,Db2 IN 谓词产生 NULL

当某些字段可以为 NULL 时,我可以使用对象作为 JPA 中条件查询的谓词吗?

React - 谓词功能组件

神奇的 SQL 之谓词 → 难理解的 EXISTS