Как работает троичный оператор с жестко закодированными возвращаемыми значениями в LINQ OrderBy? - PullRequest
0 голосов
/ 08 мая 2018

Я наткнулся на этот ответ Структура сущности OrderBy «CASE WHEN» , Я всегда использую OrderBy для заказа по определенному свойству, но не знал, как что-то подобное может быть полезным или даже существовать:

foos.OrderBy(f => f.Val3? 1 : 0);

Я создал Foo класс, чтобы посмотреть, как он работает:

class Foo
{
    public int Id { get; set; }
    public int Val1 { get; set; }
    public string Val2 { get; set; }
    public bool Val3 { get; set; }
    public override string ToString()
    {
        return string.Format($"{Id}> {Val1}, {Val2}, { Val3}");
    }
}

In Main:

List<Foo> foos = new List<Foo>
        {
            new Foo{Id=1,Val1=5, Val2= "a", Val3= true},
            new Foo{Id=2,Val1=4, Val2= "c", Val3= false},
            new Foo{Id=3,Val1=1, Val2= "f", Val3= false},
            new Foo{Id=4,Val1=2, Val2= "d", Val3= true},
            new Foo{Id=5,Val1=9, Val2= "i", Val3= true},
            new Foo{Id=6,Val1=7, Val2= "h", Val3= true},
            new Foo{Id=7,Val1=6, Val2= "g", Val3= true},
            new Foo{Id=8,Val1=8, Val2= "b", Val3= true},
            new Foo{Id=9,Val1=3, Val2= "e", Val3= false}
        };

var orderedFoos = foos.OrderBy(f => f.Val2 == "c" ? 1 : 2).ToList();

В orderedFoos первый и второй элементы поменялись местами (элемент "c" становится первым):

enter image description here

и когда:

var orderedFoos = foos.OrderBy(f => f.Val2 == "c" ? 3 : 1).ToList();

пункт "c" становится последним.

Я использовал несколько значений с разными свойствами, но не мог заметить шаблон

Ответы [ 2 ]

0 голосов
/ 08 мая 2018

Если вы это сделаете, это будет не упорядочение по этому свойству, а по значению, возвращаемому условным оператором. Таким образом, каждая запись получает «значение сортировки», а список сортируется следующим образом:

new Foo { Id=2, Val2= "c", VirtualSortValue = 1}, // because "c"
new Foo { Id=1, Val2= "a", VirtualSortValue = 2}, // because not "c"
new Foo { Id=3, Val2= "f", VirtualSortValue = 2},
new Foo { Id=4, Val2= "d", VirtualSortValue = 2},
new Foo { Id=5, Val2= "i", VirtualSortValue = 2},
new Foo { Id=6, Val2= "h", VirtualSortValue = 2},
new Foo { Id=7, Val2= "g", VirtualSortValue = 2},
new Foo { Id=8, Val2= "b", VirtualSortValue = 2},
new Foo { Id=9, Val2= "e", VirtualSortValue = 2}

Способ сортировки остатка зависит от основного хранилища (когда речь идет о Linq-to-Entities). Для использования на List<T> вы используете Enumerable.OrderBy(), чей тип гарантированно будет "стабильным" :

Этот метод выполняет стабильную сортировку; то есть, если ключи двух элементов равны, порядок элементов сохраняется. Напротив, нестабильная сортировка не сохраняет порядок элементов с одинаковым ключом.

0 голосов
/ 08 мая 2018

Изображение точно показывает, что происходит. Для лучшего понимания создайте список лямбда-оператора orderby:

C истинно, все остальные ложны, так как нет другого способа упорядочить их, единственный логический способ «сортировать» их - это в порядке их поступления (поэтому не сортировка).

Когда вы печатаете результаты, он возвращает C вверху, а затем все остальные элементы в том порядке, в котором вы их поместили.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...