我正在嘗試從 EF linq 查詢中獲取訂單 ID 串列。sql 查詢很快回傳,但我認為 EF 框架正在嘗試創建完整的物體。我只想要訂單的ID。似乎它創建了整個物體,然后將其決議為僅 id。這似乎是對資源的完全浪費。
訂單是一個包含許多子物體的復雜物件。除了串列中訂單的 ID 之外,我不需要任何東西。訂單被組織成 OrderCollection,這是一個多對多的關系。
英文的基本查詢是獲取指定訂單集合中的訂單 ID,并且購物車日期比指定日期更新,并且只發送指定頁面(跳過并接受)。
例子:
_repo.Orders.Where(o => o.OrderCollection.Any(r => r.Id == RoutingRuleId)).ToList()
.Where(o => o.OrderDate >= StartDateTime)
.OrderBy(x => x.OrderDate )
.Skip(RecordsToSkipCount)
.Take(BatchSize).Select(x => new { x.Id }).ToArray();
在除錯模式下,sql 僅在 102 毫秒內運行。但之后我看到記憶體在失敗之前達到了 4GB。批大小只有 100。它就像抓住了一切。
我嘗試移動選擇,但也失敗了,或者在運行 sql 時出現語法錯誤或性能不佳(SQL 需要 16 秒)。
例子
_repo.Orders.Select(x => new { x.Id, x.OrderCollection, x.OrderDate})
.Where(o => o.OrderCollection.Any(r => r.Id == RoutingRuleId)).ToList()
.Where(o => o.OrderDate >= StartDateTime)
.OrderBy(x => x.OrderDate )
.Skip(RecordsToSkipCount)
.Take(BatchSize).Select(x => new { x.Id }).ToArray();
該資料庫有數百萬條記錄。
uj5u.com熱心網友回復:
你所擁有的是粗略的;
List<Order> list = _repo.Orders
.Where(o => o.OrderCollection.Any(r => r.Id == RoutingRuleId))
.ToList();
list.Where(o => o.OrderDate >= StartDateTime)
.OrderBy(x => x.OrderDate )
.Skip(RecordsToSkipCount)
.Take(BatchSize)
.Select(x => new { x.Id })
.ToArray();
首先.ToList是強制 EF Core 將每個帶有匹配路由規則的訂單加載到記憶體中。然后運算式的其余部分使用IEnumerable擴展方法來處理這些結果。
我認為您想將其重新排列為;
IQueryable<Order> query = _repo.Orders
.Where(o => o.OrderCollection.Any(r => r.Id == RoutingRuleId)
&& o.OrderDate >= StartDateTime)
.OrderBy(x => x.OrderDate )
.Skip(RecordsToSkipCount)
.Take(BatchSize)
.Select(x => new { x.Id });
query.ToArray();
創建一個IQueryable不會觸發 EF Core 執行任何 SQL。AnIQueryable只是您要運行的查詢的描述。然后它是.ToArray最終將導致 EF Core 編譯并執行 sql 陳述句的方法。
轉載請註明出處,本文鏈接:https://www.uj5u.com/qita/480067.html
