Poznámka:
Přístup k této stránce vyžaduje autorizaci. Můžete se zkusit přihlásit nebo změnit adresáře.
Přístup k této stránce vyžaduje autorizaci. Můžete zkusit změnit adresáře.
SQL Server poskytuje funkce fulltextového vyhledávání , které umožňují sofistikované vyhledávání textu nad rámec jednoduchých LIKE vzorů. Fulltextové vyhledávání podporuje lingvistické porovnávání, inflexní formuláře, vyhledávání bezkontaktní komunikace a vážené hodnocení.
Poskytovatel SQL Serveru EF Core podporuje predikáty fulltextového vyhledávání (pro filtrování) i funkce hodnotné tabulkou (pro filtrování pomocí řazení).
Nastavení fulltextového vyhledávání
Před použitím fulltextového vyhledávání musíte ve své databázi vytvořit fulltextový katalog a fulltextový index sloupců, které chcete prohledat.
Poznámka:
Fulltextový katalog a správa indexů při migracích byla zavedena v EF Core 11.
Fulltextové katalogy a indexy můžete nakonfigurovat přímo v modelu EF. Když přidáte migraci, EF vygeneruje příslušný SQL pro vytvoření (nebo změnu) katalogu a indexu za vás.
Nejprve definujte fulltextový katalog modelu a pak nakonfigurujte fulltextový index pro typ entity:
protected override void OnModelCreating(ModelBuilder modelBuilder)
{
modelBuilder.HasFullTextCatalog("ftCatalog");
modelBuilder.Entity<Article>()
.HasFullTextIndex(a => a.Contents)
.HasKeyIndex("PK_Articles")
.OnCatalog("ftCatalog");
}
Metoda HasKeyIndex() určuje jedinečný index s jedním sloupcem, který není null, který se používá jako fulltextový klíč tabulky (obvykle index primárního klíče).
OnCatalog() přiřadí fulltextový index ke konkrétnímu katalogu.
Můžete také nakonfigurovat více sloupců a další možnosti, jako jsou jazyky pro jednotlivé sloupce a sledování změn:
modelBuilder.Entity<Article>()
.HasFullTextIndex(a => new { a.Title, a.Contents })
.HasKeyIndex("PK_Articles")
.OnCatalog("ftCatalog")
.WithChangeTracking(FullTextChangeTracking.Manual)
.HasLanguage("Title", "English")
.HasLanguage("Contents", "French");
Fulltextový katalog lze také nakonfigurovat jako výchozí katalog a s citlivostí na přízvuky.
modelBuilder.HasFullTextCatalog("ftCatalog")
.IsDefault()
.IsAccentSensitive(false);
Další informace najdete v dokumentaci k fulltextovém vyhledávání SQL Serveru.
Fulltextové predikáty
EF Core podporuje FREETEXT() a CONTAINS() predikáty, které se používají v Where() klauzulích k filtrování výsledků.
FREETEXT()
FREETEXT() provádí méně striktní porovnávání, vyhledávání slov na základě jejich významu, včetně inflexních formulářů (například slovesných časů a podstatných jmen v množném čísle):
var articles = await context.Articles
.Where(a => EF.Functions.FreeText(a.Contents, "veggies"))
.ToListAsync();
To se překládá na:
SELECT [a].[Id], [a].[Title], [a].[Contents]
FROM [Articles] AS [a]
WHERE FREETEXT([a].[Contents], N'veggies')
Volitelně můžete zadat jazykový termín:
var articles = await context.Articles
.Where(a => EF.Functions.FreeText(a.Contents, "veggies", "English"))
.ToListAsync();
CONTAINS()
CONTAINS() provádí přesnější porovnávání a podporuje sofistikovanější kritéria hledání, včetně předponových termínů, vyhledávání podle blízkosti a vážených termínů.
// Simple search
var articles = await context.Articles
.Where(a => EF.Functions.Contains(a.Contents, "veggies"))
.ToListAsync();
// Prefix search (words starting with "vegg")
var articles = await context.Articles
.Where(a => EF.Functions.Contains(a.Contents, "\"vegg*\""))
.ToListAsync();
// Phrase search
var articles = await context.Articles
.Where(a => EF.Functions.Contains(a.Contents, "\"fresh vegetables\""))
.ToListAsync();
To se překládá na:
SELECT [a].[Id], [a].[Title], [a].[Contents]
FROM [Articles] AS [a]
WHERE CONTAINS([a].[Contents], N'veggies')
Další informace o CONTAINS() syntaxi dotazů najdete v dokumentaci k SQL Serveru CONTAINS.
Fulltextové tabulkové funkce
Poznámka:
Funkce s fulltextovou hodnotou tabulky se zavádějí v EF Core 11.
I když výše uvedené predikáty jsou užitečné pro filtrování, neposkytují informace o řazení. Funkce SQL Serveru vracející tabulky FREETEXTTABLE() a CONTAINSTABLE() vracejí jak odpovídající řádky, tak i skóre hodnocení, které určuje, jak dobře jednotlivé řádky odpovídají vyhledávacímu dotazu.
FreeTextTable()
FreeTextTable() je verze FreeText()funkce s hodnotou tabulky . Vrátí FullTextSearchResult<TEntity>, která zahrnuje entitu i hodnotu řazení:
var results = await context.Articles
.Join(
context.Articles.FreeTextTable<Article, int>("veggies", topN: 10),
a => a.Id,
ftt => ftt.Key,
(a, ftt) => new { Article = a, ftt.Rank })
.OrderByDescending(r => r.Rank)
.ToListAsync();
foreach (var result in results)
{
Console.WriteLine($"Article {result.Article.Id} with rank {result.Rank}");
}
Všimněte si, že je nutné zadat parametry obecného typu; Article odpovídá prohledávanému typu entity, kde int je klíč fulltextového vyhledávání zadaný při vytváření indexu a který je vrácen .FREETEXTTABLE()
Výše uvedené automaticky prohledává všechny sloupce registrované pro fulltextové vyhledávání a zobrazí 10 nejlepších shod. Můžete také zadat konkrétní sloupec, který se má prohledávat:
var results = await context.Articles
.Join(
context.Articles.FreeTextTable<Article, int>(a => a.Contents, "veggies"),
a => a.Id,
ftt => ftt.Key,
(a, ftt) => new { Article = a, ftt.Rank })
.OrderByDescending(r => r.Rank)
.ToListAsync();
... nebo více sloupců:
var results = await context.Articles
.FreeTextTable(a => new { a.Title, a.Contents }, "veggies")
.Select(r => new { Article = r.Value, Rank = r.Rank })
.OrderByDescending(r => r.Rank)
.ToListAsync();
ContainsTable()
ContainsTable() je verze Contains()funkce s hodnotou tabulky , která podporuje stejnou sofistikovanou syntaxi vyhledávání a zároveň poskytuje informace o řazení:
var results = await context.Articles
.Join(
context.Articles.ContainsTable<Article, int>( "veggies OR fruits"),
a => a.Id,
ftt => ftt.Key,
(a, ftt) => new { Article = a, ftt.Rank })
.OrderByDescending(r => r.Rank)
.ToListAsync();
Omezení výsledků
Obě funkce s hodnotami tabulky podporují topN parametr pro omezení počtu výsledků:
var results = await context.Articles
.FreeTextTable(a => a.Contents, "veggies", topN: 10)
.Select(r => new { Article = r.Value, Rank = r.Rank })
.OrderByDescending(r => r.Rank)
.ToListAsync();
Určení jazyka
Obě funkce hodnotné tabulkou podporují zadání jazykového termínu pro lingvistické porovnávání:
var results = await context.Articles
.FreeTextTable(a => a.Contents, "veggies", languageTerm: "English")
.Select(r => new { Article = r.Value, Rank = r.Rank })
.ToListAsync();
Kdy použít predikáty versus tabulkově hodnotné funkce
| funkce | Predikáty (FreeText(), Contains()) |
Tabulkové funkce (FreeTextTable(), ContainsTable()) |
|---|---|---|
| Poskytuje pořadí. | ❌ Ne | ✅ Ano |
| Výkon pro velké sady výsledků | Lepší pro filtrování | Lepší pro hodnocení a řazení |
| Kombinování s jinými entitami | Spojení prostřednictvím spojení | Předdefinovaný výsledek entity |
Použití v Where() klauzuli |
✅ Ano | ❌ Ne (použít jako zdroj) |
Predikáty použijte, když jednoduše potřebujete filtrovat výsledky na základě kritérií fulltextového vyhledávání. Použijte tabulkové funkce, když potřebujete informace o řazení výsledků podle relevance nebo zobrazení jejich skóre relevance uživatelům.