Аз соли Дархостҳои LINQ Маслиҳатҳои ҷадвалро муайян кардан ғайриимкон аст, аз ин рӯ шумо бояд як намоиши дигар - "печтошка"-и шакли зеринро эҷод кунед:
CREATE VIEW ИМЯ_представления AS SELECT * FROM MAT_VIEW WITH (NOEXPAND);
4) Истифодаи функсияҳои ҷадвал
Аксар вақт дар Дархостҳои LINQ Блокҳои калони зерпурсишҳо ё блокҳое, ки бо истифода аз намудҳо бо сохтори мураккаб дархости ниҳоиро бо сохтори иҷроиши хеле мураккаб ва ноустувор ташкил медиҳанд.
Бо истифода аз тангтарин ва аз ҳама талабшавандаи маълумот:
Дар кэшҳо нигоҳ доштани маҷмӯаҳои бузурги додаҳо лозим нест (ба монанди намуди намоишҳои индексатсия), ки аз он шумо ҳоло ҳам маълумотро аз рӯи параметр филтр кунед.
Масалан, ҷадвале мавҷуд аст, ки филтри он НОҲИЯИ ПАНҶ се майдон истифода мешавад (а, б, в).
Одатан, ҳама дархостҳо шарти доимӣ доранд a = 0 ва b = 0.
Бо вуҷуди ин, дархост барои соҳаи c тағйирёбанда бештар.
Бигзор шарт a = 0 ва b = 0 Он воқеан ба мо кӯмак мекунад, ки маҷмӯи натиҷаҳоро бо ҳазорҳо сабтҳо маҳдуд кунем, аммо шарт с интихобро то сад сабт танг мекунад.
Дар ин ҷо функсияи ҷадвал метавонад як варианти беҳтар бошад.
Инчунин, функсияи ҷадвал дар вақти иҷро пешгӯишавандатар ва мувофиқ аст.
намунаи
Биёед мисоли татбиқро бо истифода аз пойгоҳи додаҳои саволҳо ҳамчун намуна дида бароем.
(@p__linq__0 nvarchar(4000))SELECT
1 AS [C1],
[Extent1].[Id] AS [Id],
[Join2].[Object_Id] AS [Object_Id],
[Join2].[ObjectType_Id] AS [ObjectType_Id],
[Join2].[Name] AS [Name],
[Join2].[ExternalId] AS [ExternalId]
FROM [dbo].[Questions] AS [Extent1]
INNER JOIN (SELECT [Extent2].[Object_Id] AS [Object_Id],
[Extent2].[Question_Id] AS [Question_Id], [Extent3].[ExternalId] AS [ExternalId],
[Extent3].[ObjectType_Id] AS [ObjectType_Id], [Extent4].[Name] AS [Name]
FROM [dbo].[ObjectQuestions] AS [Extent2]
INNER JOIN [dbo].[Objects] AS [Extent3] ON [Extent2].[Object_Id] = [Extent3].[Id]
LEFT OUTER JOIN [dbo].[ObjectTypes] AS [Extent4]
ON [Extent3].[ObjectType_Id] = [Extent4].[Id] ) AS [Join2]
ON [Extent1].[Id] = [Join2].[Question_Id]
WHERE ([Extent1].[AnswerId] IS NULL) AND (0 = [Extent1].[Exp]) AND ( EXISTS (SELECT
1 AS [C1]
FROM [dbo].[OperativeQuestions] AS [Extent5]
WHERE (([Extent5].[Email] = @p__linq__0) OR (([Extent5].[Email] IS NULL)
AND (@p__linq__0 IS NULL))) AND ([Extent5].[Id] = [Extent1].[Id])
));
Намоиш дорои сохтори хеле мураккаб аст: он дорои зерпурсишҳо мебошад ва аз навъбандӣ истифода мешавад DISTINCT, ки умуман як амалиёти хеле серталаб аст.
Намунае аз OperativeQuestions тақрибан даҳ ҳазор сабт аст.
Ва чунин ба назар мерасад, ки зерпурсиш бояд сабтҳоро як маротиба тавассути [Email] = @p__linq__0 ҳисоб кунад ва он гоҳ ин якчанд сад сабтҳо бояд бо Id бо Саволҳо пайваст карда шаванд ва дархост зуд хоҳад буд.
Дарвоқеъ, пайвасти пайдарпайи ҳамаи ҷадвалҳо вуҷуд дорад: тафтиши мукотибаи саволҳои Id бо Id аз OperativeQuestions ва филтр кардани почтаи электронӣ.
CREATE VIEW [dbo].[OperativeQuestions]
AS
SELECT DISTINCT Q.Id, USR.email AS Email
FROM [dbo].Questions AS Q INNER JOIN
[dbo].ProcessUserAccesses AS BPU ON BPU.ProcessId = CQ.Process_Id
OUTER APPLY
(SELECT 1 AS HasNoObjects
WHERE NOT EXISTS
(SELECT 1
FROM [dbo].ObjectUserAccesses AS BOU
WHERE BOU.ProcessUserAccessId = BPU.[Id] AND BOU.[To] IS NULL)
) AS BO INNER JOIN
[dbo].Users AS USR ON USR.Id = BPU.UserId
WHERE CQ.[Exp] = 0 AND CQ.AnswerId IS NULL AND BPU.[To] IS NULL
AND (BO.HasNoObjects = 1 OR
EXISTS (SELECT 1
FROM [dbo].ObjectUserAccesses AS BOU INNER JOIN
[dbo].ObjectQuestions AS QBO
ON QBO.[Object_Id] =BOU.ObjectId
WHERE BOU.ProcessUserAccessId = BPU.Id
AND BOU.[To] IS NULL AND QBO.Question_Id = CQ.Id));
CREATE FUNCTION [dbo].[OperativeQuestionsUserMail]
(
@Email nvarchar(4000)
)
RETURNS
@tbl TABLE
(
[Id] uniqueidentifier,
[Email] nvarchar(4000)
)
AS
BEGIN
INSERT INTO @tbl ([Id], [Email])
SELECT Id, @Email
FROM [OperativeQuestions] AS [x] WHERE [x].[Email] = @Email;
RETURN;
END
Ин ҷадвали арзишҳоро бо сохтори пешакии додаҳо бармегардонад.
Барои он ки дархостҳо ба OperativeQuestionsUserMail оптималӣ бошанд ва нақшаҳои оптималии дархост дошта бошанд, сохтори қатъӣ лозим аст, на Бозгашти Љадвали ҳамчун бозгашт...
(@p__linq__0 nvarchar(4000))SELECT
1 AS [C1],
[Extent1].[Id] AS [Id],
[Join2].[Object_Id] AS [Object_Id],
[Join2].[ObjectType_Id] AS [ObjectType_Id],
[Join2].[Name] AS [Name],
[Join2].[ExternalId] AS [ExternalId]
FROM (
SELECT Id, Email FROM [dbo].[OperativeQuestionsUserMail] (@p__linq__0)
) AS [Extent0]
INNER JOIN [dbo].[Questions] AS [Extent1] ON([Extent0].Id=[Extent1].Id)
INNER JOIN (SELECT [Extent2].[Object_Id] AS [Object_Id], [Extent2].[Question_Id] AS [Question_Id], [Extent3].[ExternalId] AS [ExternalId], [Extent3].[ObjectType_Id] AS [ObjectType_Id], [Extent4].[Name] AS [Name]
FROM [dbo].[ObjectQuestions] AS [Extent2]
INNER JOIN [dbo].[Objects] AS [Extent3] ON [Extent2].[Object_Id] = [Extent3].[Id]
LEFT OUTER JOIN [dbo].[ObjectTypes] AS [Extent4]
ON [Extent3].[ObjectType_Id] = [Extent4].[Id] ) AS [Join2]
ON [Extent1].[Id] = [Join2].[Question_Id]
WHERE ([Extent1].[AnswerId] IS NULL) AND (0 = [Extent1].[Exp]);
Харитасозии намудҳо ва функсияҳо дар DbContext (EF Core 2)
public class QuestionsDbContext : DbContext
{
//...
public DbQuery<OperativeQuestion> OperativeQuestions { get; set; }
//...
protected override void OnModelCreating(ModelBuilder modelBuilder)
{
modelBuilder.Query<OperativeQuestion>().ToView("OperativeQuestions");
}
}
public static class FromSqlQueries
{
public static IQueryable<OperativeQuestion> GetByUserEmail(this DbQuery<OperativeQuestion> source, string Email)
=> source.FromSql($"SELECT Id, Email FROM [dbo].[OperativeQuestionsUserMail] ({Email})");
}