Почему LINQ-to-Entites распознает мой собственный метод?

Это работает:

Entities.WorkOrderSet.Where(MyCustomMethod);

Это не означает:

Entities.WorkOrderSet.Where(o => MyCustomMethod(o));

( [Изменить] Даже без new он не работает)

Я понимаю, почему вторая не работает - , но почему в мире первая работа!? Не следует ли мне получать "LINQ-to-Entities", который не распознает метод.. "во время выполнения, как со вторым?

Для справки, здесь MyCustomMethod

public bool MyCustomMethod(WorkOrder workOrder)
{
    return !workOrder.WorkOrderNum.StartsWith("A", StringComparison.CurrentCultureIgnoreCase);
}

Использование EF1, а не EF4

Ответ 1

Сначала работает, потому что он является методом расширения и выполняет запрос как func, а затем фильтрует ваш список see здесь. Таким образом, в общем случае он автоматически добавляет, где

 Where(Func<WorkOrder, bool>

Второе не потому, что оно подталкивает ваше утверждение where к db. Когда вычисляется лямбда-выражение, оно расширяется следующим образом:

Where( Expresion<Func<WorkOrder, bool>>)

Вот хорошая статья которая объясняет Выражения vs Func

Вот еще одно сообщение, которое помогает объяснить разницу

[Изменить (BlueRaja)]

Это новое редактирование выглядит правильным. Чтобы прояснить: кажется, что Func<WorkOrder, bool> неявно приписано к Expression<Func<WorkOrder, bool>>, но не наоборот.

Существуют перегрузки Where для обоих типов. .Where(MyCustomMethod) вызывает Func<WorkOrder, bool> one, тогда как .Where(o => MyCustomMethod(o)) вызывает Expression<Func<WorkOrder, bool>> one.

Ответ 2

Просто создавая это как "ответ" здесь, вместо комментария.

Я думаю, что это новая функция в .NET 4, где структура понимает, что эта функция не может быть переведена на SQL, но может быть легко обработана в памяти. Таким образом, он получает весь набор данных на локальном компьютере и продолжает обработку запросов.

Это ваш первый фрагмент, когда он переводится в дерево выражений, прямо скажет, что он запускает внешний метод, в то время как ваш второй фрагмент не так "прямой". Полагаю, именно поэтому в первом случае L2E может легко понять, что происходит, и решить, что делать, а во втором случае "думает", что лучше отправить исключение и позволить разработчикам почесывать головы еще немного _ _ ​​^