FullTextSearch可选单词

时间:2017-03-23 17:10:41

标签: c# sql sql-server full-text-search

在桌面上使用MS SQL 2016全文搜索,用户搜索"快速棕狐"。这不会返回任何结果,因为所有三个单词都不会出现在任何单个记录中。但是"快速的棕色"返回结果,"棕色狐狸"和"快狐"。

有没有办法构造输入查询,因此单词是可选的(即用户说"快速棕色*狐狸"表示狐狸是可选的)或者查询本身返回没有所有单词的结果?我不介意运行两个查询,第一个用于所有单词,如果第一个没有返回任何行,则再次输入不完整的输入。

string query = String.Concat(@"
    SELECT *
    FROM FullTextSearches AS FT_TBL INNER JOIN
    CONTAINSTABLE(FullTextSearches, (Title, Body), @SearchCondition) AS KEY_TBL
    ON FT_TBL.Id = KEY_TBL.[KEY]
    WHERE (FT_TBL.Accessibility = 0) OR ((FT_TBL.Accessibility & @Roles) > 0)
    ORDER BY KEY_TBL.[RANK] DESC
    OFFSET (@Skip) ROWS FETCH NEXT (@Take) ROWS ONLY");

SqlParameter paramSearch = new SqlParameter("SearchCondition", "\"" + searchTerm + "\"");
SqlParameter paramSkip = new SqlParameter("Skip", pageNumber * pageSize);
SqlParameter paramTake = new SqlParameter("Take", pageSize);
SqlParameter paramRoles = new SqlParameter("Roles", accessibility);
object[] parameters = new object[] { paramSearch, paramSkip, paramTake, paramRoles };
var results = db.FullTextSearch.SqlQuery(query, parameters);

一直在学习。

1 个答案:

答案 0 :(得分:1)

我认为这样的事情会让你到那儿。不是多个查询,而是多个连接。

string searchTerm = "quick brown *fox"
string withOptional = searchTerm.Replace("*", "");
string withoutOptional = Regex.Replace(searchTerm, "[*]\w", "");

string[] options = new string[]{ withOptional, withoutOptional }; 

string query = String.Concat(@"
    SELECT *
    FROM FullTextSearches AS FT_TBL ");

int i = 1;
List<SqlParameter> parameters = new List<SqlParameter>();

foreach(string option in options)
{
    parameters.Add(new SqlParameter("SearchCondition" + (i++).ToString(), "\"" + option + "\""))
    query += $@"LEFT JOIN CONTAINSTABLE(FullTextSearches, (Title, Body), @SearchCondition{i - 1}) AS KEY_TBL{i - 1} ON FT_TBL.Id = KEY_TBL{i - 1}.[KEY] ";
}

SqlParameter paramSkip = new SqlParameter("Skip", pageNumber * pageSize);
SqlParameter paramTake = new SqlParameter("Take", pageSize);
SqlParameter paramRoles = new SqlParameter("Roles", accessibility);
object[] parms = new object[parameters.Length + 3];

for (j = 0; j < parameters.Length; j++)
{
    parms[j] = parameters[j];
}

parms[parms.Length - 3] = paramSkip;
parms[parms.Length - 2] = paramTake;
parms[parms.Length - 1] = paramRoles;

var results = db.FullTextSearch.SqlQuery(query, parms);


string query += String.Concat(@"
    WHERE (FT_TBL.Accessibility = 0) OR ((FT_TBL.Accessibility & @Roles) > 0)
    ORDER BY KEY_TBL.[RANK] DESC
    OFFSET (@Skip) ROWS FETCH NEXT (@Take) ROWS ONLY");