Сравнение дней в Linq

#c# #asp.net #.net #sql-server #linq

#c# #asp.net #.net #sql-сервер #linq

Вопрос:

В таблице есть набор записей с созданным полем даты. Как мне выбрать все записи, которые были созданы в данный день недели. например, все записи, которые были созданы в понедельник, это может быть этот понедельник, прошлый понедельник или предыдущий понедельник.

Это то, что я написал до сих пор:

 from ob in obList
where SqlFunctions.DateDiff("days", today, ob.StartDate) % 7 == 0
select ob.CustomerOnboardingId
  

Но я получаю сообщение об ошибке по этому:

{«Эта функция может быть вызвана только из LINQ для объектов».}

Обновление 1:

obList — это коллекция в памяти. А today — это переменная, которая содержит DateTime.Сегодня;

Комментарии:

1. Что такое obList ?

2. obList — это коллекция в памяти. Теперь я обновил вопрос

Ответ №1:

Вам не нужно вызывать эту функцию, чтобы получить разницу в днях, которая, как указано в исключении, может использоваться только в Linq to Entities. В Linq to Objects вы можете выполнить следующее:

 from ob in obList
where (today - ob.StartDate).TotalDays  % 7 == 0
select ob.CustomerOnboardingId
  

Комментарии:

1. Зависит от того, что obList такое. Похоже на переменную в памяти, основанную на имени, но OP говорит, что она представляет таблицу. Вы могли бы использовать AsEnumerable() для принудительной оценки в C #, а не в DB, но это приводит к значительному снижению производительности, если это большая таблица базы данных.

2. Согласен @EricJ, я предполагаю, что obList это коллекция, которая находится в памяти.

3. in a table казалось бы, это предположение недействительно, но, надеюсь, OP прояснит его.

4. Извините за путаницу. ob — это коллекция в памяти

5. Но, честно говоря, я думал, что это не будет иметь значения, потому что я думал, что Linq работает почти одинаково со всем набором данных

Ответ №2:

Как указано в ошибке, вы пытаетесь выполнить метод Linq для объектов в памяти, который не может быть выполнен. Когда выполняется запрос linq в контексте Linq2SQL или EF, он преобразуется в sql, и именно тогда функции, подобные той, которую вы использовали, получают свое значение — они реализуют, как это сделать в sql. В коллекциях в памяти они не имеют значения.

(Это похоже на то, что вы попытаетесь выполнить метод, определенный в вашем коде, в запросе linq-to-entities и получите, что он не поддерживается linq-to-entities)

Вместо вычисления (day1 - day2) % 7 вы можете использовать DayOfWeek свойство DateTime :

 DateTime day = new DateTime(2016, 1, 15); // Friday

List<dynamic> collection = new List<dynamic>
{
    new { CustomerOnboardingId = "Item1", StartDate = new DateTime(2016,1,1) }, // Friday
    new { CustomerOnboardingId = "Item2", StartDate = new DateTime(2016,1,2) },
    new { CustomerOnboardingId = "Item3", StartDate = new DateTime(2016,1,8) }, // Friday
};

var result = (from item in collection
              where item.StartDate.DayOfWeek == day.DayOfWeek
              select item.CustomerOnboardingId).ToList();

// result = Item1, Item3
  

Комментарии:

1. @Libin Джозеф — Рад, что это тебе помогло 🙂