我想检查给定文本中的任何顺序是否存在所有给定的单词片段。
片段由Web应用程序用户以单个字符串提供,由'abc xyz kj'之类的空格分隔。它们存在于'mn kj qabc pc xyzw'中,但在'mn kj qabc pc xyw'中不存在。
我编写了以下功能,但它看起来很复杂,所以我一定做错了。关于不同方法的任何想法或如何使其表现?
BTW数据库只为我读取,因此我无法对其进行全文索引,而且所有者也不会这样做。
create function dbo.tem_fragmentos(
@texto varchar(max),
@fragmentos varchar(max)
)
returns bit as
begin
declare
@inicio integer = 1,
@fim integer,
@fragmento varchar(max);
set @fragmentos = ltrim(rtrim(@fragmentos));
while charindex(' ', @fragmentos) > 0
set @fragmentos = replace(@fragmentos, ' ', ' ');
while @inicio <= len(@fragmentos) begin
set @fim = charindex(' ', @fragmentos, @inicio + 1);
if @fim = 0 set @fim = len(@fragmentos) + 1;
set @fragmento = substring(@fragmentos, @inicio, @fim - @inicio);
if charindex(@fragmento, @texto) = 0 return 0;
set @inicio = @fim + 1;
end -- while
return 1;
end;
select dbo.tem_fragmentos('clodoaldo pinto neto', ' clo cl nto pinto');
答案 0 :(得分:1)
我就是这样做的。不确定它是不是很复杂......
Create Function dbo.tem_fragmentos
(
@texto varchar(max),
@fragmentos varchar(max)
)
Returns Bit As
Begin
Declare @table Table (fragmentos Varchar(Max))
Set @fragmentos = Ltrim(Rtrim(@fragmentos))
While @fragmentos <> ''
Begin
Insert @table (fragmentos)
Select Left(@fragmentos,Charindex(' ',@fragmentos+' ')-1)
Set @fragmentos = Ltrim(Rtrim(Right(@fragmentos,Len(@fragmentos)-(Charindex(' ',@fragmentos+' ')-1))));
end
If Exists (Select 1
From @table t
Where @texto Not Like '%' + fragmentos + '%')
Begin
Return 0;
End
Return 1;
End;
Select dbo.tem_fragmentos('clodoaldo pinto neto', ' clo cl nto pinto');
答案 1 :(得分:0)
我假设你的文本存在于db表中,否则你不会让db服务器完成工作。那么,为什么不让你的应用程序在空格上打破字符串并构建动态SQL,如:
select *
from MyTable
where charindex('abc', MyColumn) > 0
and charindex('xyz', MyColumn) > 0
and charindex('kj', MyColumn) > 0
<强>更新强>
如果您不想使用动态SQL,我会将输入拆分为应用程序中的单词,然后使用表值参数(TVP)将单词列表传递给查询。然后,这是一个简单的左连接,以确定它们是否匹配。
答案 2 :(得分:0)
听起来像通配符LIKE
搜索应该适合您:
declare @texto varchar(max) = 'mn kj q abc pc xyzw',
@fragmentos varchar(max) = 'abc xyz kj'
/*
yes = 'mn kj qabc pc xyzw'
no = 'mn kj qabc pc xyw'
*/
--use your own number table
declare @number table (n int identity(1,1) primary key clustered, x char(1) null);
insert into @number(x)
select top 1000 null from master..spt_values
select [IsMatch] = min(case when @texto like '%'+substring(@fragmentos, n, charindex(' ', @fragmentos + ' ', n) - n)+'%' then 1 else 0 end)
from @number
where n <= datalength(@fragmentos)+1 and
substring(' ' + @fragmentos, N, 1) = ' ';