在 sql 服务器中检查字段是否包含多个字符串
Checking if field contains multiple string in sql server
我正在开发一个 sql 数据库,它将提供一些网格数据。网格将启用过滤、排序和分页,但也有严格的要求,例如用户可以在网格上方的文本输入中输入自由文本
'Engine 1001 Requi' 并且结果将仅包含在某些列中包含所有文本片段的行。因此,一列可能包含 Engine,另一列可能包含 1001,而其他一些列可能包含 Requi。
我在 table(我们称它为 myTable)中创建了一个技术专栏(我们称它为 myTechnicalColumn),每次有人插入或更新一行时都会更新它,它将包含所有的所有值用 space.
合并和分隔的列
现在要将它与 entity framework 一起使用,我决定使用一个 table 值函数,它接受一个参数 @searchQuery 并且它将像这样处理它:
CREATE FUNCTION myFunctionName(@searchText NVARCHAR(MAX))
RETURNS @Result TABLE
( ... here come columns )
AS
BEGIN
DECLARE @searchToken TokenType
INSERT INTO @searchToken(token) SELECT value FROM STRING_SPLIT(@searchText,' ')
DECLARE @searchTextLength INT
SET @searchTextLength = (SELECT COUNT(*) FROM @searchToken)
INSERT INTO @Result
SELECT
... here come columns
FROM myTable
WHERE (SELECT COUNT(*) FROM @searchToken WHERE CHARINDEX(token, myTechnicalColumn) > 0) = @searchTextLength
RETURN;
END
这个解决方案当然可以正常工作,但速度有点慢。任何提示如何提高其效率?
由于没有数据可以测试,我不确定以下是否能解决您的问题:
-- Replace the last INSERT portion
INSERT INTO @Result
SELECT
... here come columns
FROM myTable T
JOIN @searchToken S ON CHARINDEX(S.token, T.myTechnicalColumn) > 0
您可以使用内联 Table 值函数,这应该快得多。
这将是您当前代码的直接翻译
CREATE FUNCTION myFunctionName(@searchText NVARCHAR(MAX))
RETURNS TABLE
AS RETURN
(
WITH searchText AS (
SELECT value token
FROM STRING_SPLIT(@searchText,' ') s(token)
)
SELECT
... here come columns
FROM myTable t
WHERE (
SELECT COUNT(*)
FROM searchText
WHERE CHARINDEX(s.token, t.myTechnicalColumn) > 0
) = (SELECT COUNT(*) FROM searchText)
);
GO
您正在使用一种名为 无余数关系除法 的查询形式,还有其他方法可以解决这个问题:
CREATE FUNCTION myFunctionName(@searchText NVARCHAR(MAX))
RETURNS TABLE
AS RETURN
(
WITH searchText AS (
SELECT value token
FROM STRING_SPLIT(@searchText,' ') s(token)
)
SELECT
... here come columns
FROM myTable t
WHERE NOT EXISTS (
SELECT 1
FROM searchText
WHERE CHARINDEX(s.token, t.myTechnicalColumn) = 0
)
);
GO
这可能会更快或更慢,具体取决于多种因素,您需要进行测试。
我正在开发一个 sql 数据库,它将提供一些网格数据。网格将启用过滤、排序和分页,但也有严格的要求,例如用户可以在网格上方的文本输入中输入自由文本 'Engine 1001 Requi' 并且结果将仅包含在某些列中包含所有文本片段的行。因此,一列可能包含 Engine,另一列可能包含 1001,而其他一些列可能包含 Requi。
我在 table(我们称它为 myTable)中创建了一个技术专栏(我们称它为 myTechnicalColumn),每次有人插入或更新一行时都会更新它,它将包含所有的所有值用 space.
合并和分隔的列现在要将它与 entity framework 一起使用,我决定使用一个 table 值函数,它接受一个参数 @searchQuery 并且它将像这样处理它:
CREATE FUNCTION myFunctionName(@searchText NVARCHAR(MAX))
RETURNS @Result TABLE
( ... here come columns )
AS
BEGIN
DECLARE @searchToken TokenType
INSERT INTO @searchToken(token) SELECT value FROM STRING_SPLIT(@searchText,' ')
DECLARE @searchTextLength INT
SET @searchTextLength = (SELECT COUNT(*) FROM @searchToken)
INSERT INTO @Result
SELECT
... here come columns
FROM myTable
WHERE (SELECT COUNT(*) FROM @searchToken WHERE CHARINDEX(token, myTechnicalColumn) > 0) = @searchTextLength
RETURN;
END
这个解决方案当然可以正常工作,但速度有点慢。任何提示如何提高其效率?
由于没有数据可以测试,我不确定以下是否能解决您的问题:
-- Replace the last INSERT portion
INSERT INTO @Result
SELECT
... here come columns
FROM myTable T
JOIN @searchToken S ON CHARINDEX(S.token, T.myTechnicalColumn) > 0
您可以使用内联 Table 值函数,这应该快得多。
这将是您当前代码的直接翻译
CREATE FUNCTION myFunctionName(@searchText NVARCHAR(MAX))
RETURNS TABLE
AS RETURN
(
WITH searchText AS (
SELECT value token
FROM STRING_SPLIT(@searchText,' ') s(token)
)
SELECT
... here come columns
FROM myTable t
WHERE (
SELECT COUNT(*)
FROM searchText
WHERE CHARINDEX(s.token, t.myTechnicalColumn) > 0
) = (SELECT COUNT(*) FROM searchText)
);
GO
您正在使用一种名为 无余数关系除法 的查询形式,还有其他方法可以解决这个问题:
CREATE FUNCTION myFunctionName(@searchText NVARCHAR(MAX))
RETURNS TABLE
AS RETURN
(
WITH searchText AS (
SELECT value token
FROM STRING_SPLIT(@searchText,' ') s(token)
)
SELECT
... here come columns
FROM myTable t
WHERE NOT EXISTS (
SELECT 1
FROM searchText
WHERE CHARINDEX(s.token, t.myTechnicalColumn) = 0
)
);
GO
这可能会更快或更慢,具体取决于多种因素,您需要进行测试。