希望我不再重复这个问题。我在这里和谷歌做了一些搜索,然后再在这里发布。

我正在使用启用了全文本的SQL Server 2008R2运行eStore。

我的要求


有一个产品表,其中包含该产品适合的产品名称,OEM代码,型号。所有内容均为文字。
我创建了一个名为TextSearch的新列。这具有此产品适用的产品名称,OEM代码和型号的串联值。这些值以逗号分隔。
当客户输入关键字时,我们在TextSearch列上运行搜索以匹配产品。请参阅下面的匹配逻辑。


我使用的是混合全文,通常喜欢进行搜索。这给出了更相关的结果。在临时表中执行的所有查询均返回。

匹配逻辑


运行以下SQL以获取全文的相关产品。但是@Keywords将被预处理。说“ CLC 2200”将更改为“ CLC * AND 2200 *”

从dbo.product的位置选择ID(TextSearch,@ Keywords)
另一个查询将使用正常的赞运行。因此,“ CLC 2200”将被预处理为“像%clc%这样的TextSearch和像%2200%这样的TextSearch”。这仅仅是因为全文搜索不会在关键字之前搜索模式。例如,它不会返回“ pclc 2200”。

从dbo.Product中选择ID,其中TextSearch如'%clc%'和TextSearch如'%2200%'
如果第1步和第2步未返回任何记录,则将执行以下搜索。我对值135进行了微调,以返回更多相关记录。

从dbo.Product中选择p.id,作为p内联接FREETEXTTABLE(product,TextSearch,@ Keywords)作为p.Id = r。[r] r.RANK> 135


上述所有组合都能以合理的速度正常运行,并返回关键字的相关产品。

但是,当根本没有找到产品时,我正在寻求进一步的改进。

假设客户寻找“ CLC 2200npk”而该产品不存在,我需要在“ CLC 2200”旁边显示下一个。

到目前为止,我尝试使用Soundex()函数。购买TextSearch列中每个单词的计算soundex值,并与关键字的soudex值进行比较。但这会返回太多的记录,而且速度也很慢。

例如,“ CLC 2200npk”将返回“ CLC 1100”等产品。但这并不是一个好结果。由于它不接近CLC 2200npk

还有一个很好的here。但这使用CLR函数。但是我无法在服务器上安装CLR功能。

所以我的逻辑应该是

如果未找到“ CLC 2200npk”,则显示“ CLC 2200”附近的内容
如果未找到“ CLC 2200”,则在“ CLC 1100”旁边显示下一个关闭

问题


是否可以按照建议进行匹配?
如果我需要进行拼写校正和搜索,那是什么好方法?我们所有的产品清单都是英文的。
是否有UDF或SP可以匹配我的建议的文本?


谢谢。

最佳答案

特定于域的快速解决方案可能是使用SOUNDEX和2个字符串之间的数字距离来计算字符串相似度。仅当您具有很多产品代码时,这才真正有用。

使用如下所示的简单UDF,您可以从字符串中提取数字字符,以便可以从“ CLC 2200npk”中获得2200,从“ CLC 1100”中获得1100,因此现在可以基于每个输入的SOUNDEX输出确定紧密度以及每个输入的数字部分的紧密度。

CREATE Function [dbo].[ExtractNumeric](@input VARCHAR(1000))
RETURNS INT
AS
BEGIN
    WHILE PATINDEX('%[^0-9]%', @input) > 0
    BEGIN
        SET @input = STUFF(@input, PATINDEX('%[^0-9]%', @input), 1, '')
    END
    IF @input = '' OR @input IS NULL
        SET @input = '0'
    RETURN CAST(@input AS INT)
END
GO


就通用算法而言,根据数据集的大小和性能要求,有几种方法可以帮助您获得不同程度的成功。 (两个链接都有可用的TSQL实现)


Double Metaphone-这种算法将以比速度更快的代价提供比soundex更好的匹配效果,尽管它确实对拼写校正非常有用。
Levenshtein Distance-这将计算将一个字符串转换为另一个字符串(例如,从“ CLC 2200npk”到“ CLC 2200”)需要多少次按键,而从“ CLC 2200npk”到“ CLC 1100”是5次。


Here是一篇有趣的文章,将两种算法结合使用,可能会给您一些想法。

希望其中一些有所帮助。

编辑:Here是一个更快的部分Levenshtein Distance实现(请阅读它不会返回与正常结果完全相同的结果的帖子)。在我的125000行的测试表上,它的运行时间为6秒,而我链接到的第一个表则为60秒。

10-01 05:08