Warning: file_get_contents(/data/phpspider/zhask/data//catemap/7/sql-server/26.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 使用EFCore在MSSQL varchar字段中搜索多个单词_C#_Sql Server_Asp.net Core_Entity Framework Core - Fatal编程技术网

C# 使用EFCore在MSSQL varchar字段中搜索多个单词

C# 使用EFCore在MSSQL varchar字段中搜索多个单词,c#,sql-server,asp.net-core,entity-framework-core,C#,Sql Server,Asp.net Core,Entity Framework Core,我的项目使用ASP.NETCore1.1、EFCore和SQLServer数据库 我有一个字符串数组,应该在文本字段中搜索,实际上字段是一个标签列表,数组是一个标签数组 完整场景: 在我的服务器端.Net内核上,我有一个标记数组{'tag2','tag4'} 每个位置都存储在SQL Server中,标记列表以“tag1、tag2、tag3”分隔 我想得到20个最近的地方,至少匹配一个标签 我曾考虑过将datatable作为参数传递给具有自定义类型参数的SQL函数,但是直到v2,datatable

我的项目使用ASP.NETCore1.1、EFCore和SQLServer数据库

我有一个字符串数组,应该在文本字段中搜索,实际上字段是一个标签列表,数组是一个标签数组

完整场景:

在我的服务器端.Net内核上,我有一个标记数组{'tag2','tag4'}

每个位置都存储在SQL Server中,标记列表以“tag1、tag2、tag3”分隔

我想得到20个最近的地方,至少匹配一个标签

我曾考虑过将datatable作为参数传递给具有自定义类型参数的SQL函数,但是直到v2,datatable类型才包含在.Net核心中

实体DbContext类中的C代码类似于:

decimal lat=2.0, lng=3.0; float maxRadius=50000;
var tags = new Array<string>(){"tag1", "tag2"};

var places = await this.Set<Place>()
               .FromSql("SELECT * FROM GetPlaces(@p0, @p1, @p2, @p3, @p4)", maxResults, lat, lng, maxRadius, tags).ToListAsync();
使用SQL函数,该函数将是:

CREATE FUNCTION [dbo].[GetClosestPlaces]
    (@lat decimal,@lng decimal,@maxRadius float=50000)
RETURNS TABLE AS RETURN 
    SELECT * FROM Places 
        WHERE ([geography]::Point(@lat,@lng,(4326)))
            .STDistance(([geography]::Point([Latitude],[Longitude],(4326)))) 
            < @maxDistance
有什么建议吗

目标是在SQL方面减少资源消耗,在这两方面,减少时间消耗的服务应该提供非常快速的答案,因为它可能会被调用多次相同的查询

目前,我还没有在数据库中找到任何好的解决方案。因此,我使用其他过滤器距离预过滤数据库数据,然后在内存中应用文本过滤器。
它的效率要高得多:SQL解决方案为500毫秒,而linq解决方案为100-150毫秒。

在这种情况下可以使用“SQL Server全文索引”吗?我想可以,但我从未使用过:它是受DTU限制的Azure DB。“标记”最多为varchar20,标记字段为varchar255您可以在SQL Azure中跨多个字段启用全文搜索。但是,您不能直接在EF中查询索引。但是,您可以很容易地使用全文索引执行自定义查询字符串。是否可以对包含的单词进行参数化?例如:在CONTAINSTags、@prm1+'或'+@prm2'中,这种语法看起来很奇怪-不是很干净。。。我找到的唯一解决方案是添加几个带有1个参数的“contains”约束。
var places = await (from p in this.Set<Place>()
         .FromSql("SELECT * FROM GetClosestPlaces(@p0, @p1, @p2)", lat, lng, maxRadius)
         where (from t in tags where p.Tags.Contains(t) select t).Any()
         select p).Take(maxResults).ToListAsync();
CREATE FUNCTION [dbo].[GetClosestPlaces]
    (@lat decimal,@lng decimal,@maxRadius float=50000)
RETURNS TABLE AS RETURN 
    SELECT * FROM Places 
        WHERE ([geography]::Point(@lat,@lng,(4326)))
            .STDistance(([geography]::Point([Latitude],[Longitude],(4326)))) 
            < @maxDistance