Я реализовал общий репозиторий для Entity Framework 4. Вот упрощенная версия, где AllAppContainer - это контекст объекта EF4:
public class Repository<T> where T : class
{
protected AllAppContainer objectContext;
protected ObjectSet<T> entitySet;
public Repository()
{
objectContext = new AllAppContainer();
entitySet = objectContext.CreateObjectSet<T>();
}
public int QueryCount(Func<T, bool> predicate)
{
int queryCount = entitySet.Count(predicate);
return queryCount;
}
}
Одним из методов является QueryCount (), который я хочу использовать как select Count (*) ... где строка SQL (не возвращая фактические записи).
Прямодушная? Вы могли бы подумать ... Во-первых, давайте сделаем не-репозиторий версию того же самого, выполняя подсчет сущностей Item:
AllAppContainer allAppContainer = new AllAppContainer();
int nonRepCount = allAppContainer.Items.Count(item => item.Id > 0);
SQL Server Profiler говорит, что сгенерированный SQL:
SELECT
[GroupBy1].[A1] AS [C1]
FROM ( SELECT
COUNT(1) AS [A1]
FROM [dbo].[Items] AS [Extent1]
WHERE [Extent1].[Id] > 0
) AS [GroupBy1]
Woo-Hoo! Оценка!
Теперь давайте вызовем то же самое, используя мой репозиторий QueryCount:
Repository<Item> repository = new Repository<Item>();
int repCount = repository.QueryCount(item => item.Id > 0);
Вот сгенерированный SQL:
SELECT
[Extent1].[Id] AS [Id],
[Extent1].[SmallField] AS [SmallField]
FROM [dbo].[Items] AS [Extent1]
Да, EF возвращает полный набор данных, затем вызывает Count () для него в памяти.
Ради интереса я попытался изменить соответствующую строку в репозитории QueryCount на:
int queryCount = new AllAppContainer().CreateObjectSet<T>().Count(predicate);
и строка без хранилища:
int nonRepCount = allAppContainer1.CreateObjectSet<Item>().Count(item => item.Id > 0);
но сгенерированный SQL для каждого такой же, как и раньше.
Теперь, почему все эти репозитории возвращают все совпадающие записи, а затем рассчитывают, когда это не для не репозитория? И есть ли способ сделать то, что я хочу, через мой общий репозиторий, то есть считать в дБ. Я не могу принять удар производительности в памяти.