Есть табличка с расписанием (день недели + где), в основе лежит enum DayOfWeek
public class Schedule
{
public int Id { get; set; }
public DayOfWeek DayOfWeek { get; set; }
public int? PlaceId { get; set; }
public Place Place { get; set; }
[Required]
[MaxLength(50)]
public string Notes { get; set; }
}
И мне для людей приходится делать сортировку по возрастанию дней недели, например:
return await this.ApplicationDbContext.Schedule
.Where(x => x.PlaceId != null)
.OrderBy(x => x.DayOfWeek)
.AsNoTracking()
.ToListAsync();
И всё было бы прекрасно, но сайт делается для тех стран, где неделя начинается с понедельника (Россия), а не с воскресенья.
А DayOfWeek начинается с воскресенья:
public enum DayOfWeek
{
Sunday,
Monday,
Tuesday,
Wednesday,
Thursday,
Friday,
Saturday,
}
Есть ли какой-то простой способ указать сортировку "первый день недели - понедельник"?
Ответ
Попробуйте "магию" (на самом деле это просто циклический сдвиг дней внутри недели):
.OrderBy(x => ((int)x.DayOfWeek + 6) % 7)
В дерево выражений эта лямбда раскладывается нормально, думаю, EF сумеет транслировать это дерево в SQL-запрос (сам не проверял).
Метод хорош тем, что простой сменой константы 6 можно сменить и требуемое начало недели.
Как спрятать формулу и привести запрос в более читабельный вид можно посмотреть в этом топике: Как составить дерево выражения для лямбды?
Дополнение. Действительно, подобный запрос транслируется вполне нормально.
Исходный запрос был:
SELECT
[t0].[Id],
[t0].[DayOfWeek],
[t0].[Notes],
[t0].[PlaceId]
FROM [Schedule] AS [t0]
WHERE [t0].[PlaceId] IS NOT NULL
ORDER BY [t0].[DayOfWeek]
Со сдвигом дня недели получается такой:
-- Region Parameters
DECLARE @p0 Int = 6
DECLARE @p1 Int = 7
-- EndRegion
SELECT
[t0].[Id],
[t0].[DayOfWeek],
[t0].[Notes],
[t0].[PlaceId]
FROM [Schedule] AS [t0]
WHERE [t0].[PlaceId] IS NOT NULL
ORDER BY ([t0].[DayOfWeek] + @p0) % @p1
Комментариев нет:
Отправить комментарий