EF架構~linq模擬left join的兩種寫法,性能差之千里!


回到目錄

對於SQL左外連接我想沒什么可說的,left join將左表數據都獲出來,右表數據如果在左表中不存在,結果為NULL,而對於LINQ來說,要實現left join的效果,也是可以的,在進行join時直接into到集合變量就可以了,但在賦值時,如果只需要集合的一條記錄,那在寫法上又會有兩種,而這兩種寫法所產生的性能是相關千里的,下面來看一下.

首先是SQL的左外連接

SELECT  [t6].[CourseID] ,
        [t6].[UserID] ,
        [t6].[CourseName] ,
        [t6].[ResourceID] ,
        [t6].[StudyTime] ,
        [t6].[BeginTime] ,
        [t6].[EndTime] ,
        [t6].[value] AS [CategoryID] ,
        [t6].[value2] AS [ClassHour] ,
        [t6].[value3] AS [Percent] ,
        [t6].[test] ,
        [t6].[ID] ,
        [t6].[SmallPicture]
FROM    dbo.User_Course AS t6
        LEFT  OUTER JOIN [User_StudyRecord] AS t3 ON t6.UserID = t3.UserID
                                                     AND t3.ResourceID = t6.ResourceID

當它被翻譯成LINQ之后,是分頁產生的結果,所以感覺更很亂了,呵呵,(LINQ在翻譯SQL時,本來就夠亂的,再一分頁,用上row_number,更亂了),但結果是一樣的,

咱們就不管微軟是怎么翻譯的了

我們重要是看一下,實現時LINQ代碼的寫法

第一種,性能低下的,如果結果為20條記錄,那它需要多連接20次

            var linq = from _data in new User_Course(UnitOfWork).GetEntities()
                       let list = new Res_Item(UnitOfWork).GetEntities().Select(t => new Entity.Res_Item
                       {
                           ID = t.ID,
                           SmallPicture = t.SmallPicture,
                       }).Where(i => i.ID == _data.ResourceID)
           
                       let list2 = new User_StudyRecord(UnitOfWork).GetModel().Select(r => new Entity.User_StudyRecord
                       {
                           StudyContent = r.StudyContent,
                           UserID = r.UserID,
                           Res_ItemID = r.Res_ItemID,
                       }).Where(i => i.Res_ItemID == _data.ResourceID && i.UserID == _data.UserID)
                       from record in list2.DefaultIfEmpty()
                       where _data.CategoryID != (int)CustomEnum.CategoryType.BroadcastProgram
                       && _data.CategoryID != (int)CustomEnum.CategoryType.AskRoom
                       select new Entity.User_Course
                       {
                           CourseID = _data.CourseID,
                           UserID = _data.UserID,
                           CourseName = _data.CourseName,
                           ResourceID = _data.ResourceID,
                           StudyTime = _data.StudyTime,
                           BeginTime = _data.BeginTime,
                           EndTime = _data.EndTime,
                           CategoryID = _data.CategoryID ?? 2,
                           Res_Item = list.FirstOrDefault(),
                           ClassHour = _data.ClassHour ?? 0,
                           Percent = _data.Percent ?? 0,
                           Prev_ResourceName = record == null ? string.Empty : record.StudyContent,
                       };

第二種,性能較好的

總結:對於第一種性能較差的寫法產生的結果,類似於LINQ本身提交的延時加載,即結果集中,每條記錄都去查詢數據庫,它不會一次將數據獲出來,這種作用在特定場合是

有它的好處的,但不適用於所有,當返回結果集比較大時,不應該使用延時加載!

回到目錄


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM