Próbuję posortować listę produktów według ich ceny.
Zestaw wyników musi zawierać listę produktów według ceny od najniższej do najwyższej według kolumny LowestPrice
. Jednak ta kolumna ma wartość null.
Mogę posortować listę malejąco w następujący sposób:
var products = from p in _context.Products
where p.ProductTypeId == 1
orderby p.LowestPrice.HasValue descending
orderby p.LowestPrice descending
select p;
// returns: 102, 101, 100, null, null
Jednak nie mogę dowiedzieć się, jak posortować to w kolejności rosnącej.
// i'd like: 100, 101, 102, null, null
orderby p.LowestPrice ?? Int.MaxValue;
to prosty sposób.OrderByDescending, ThenBy
jest jaśniejsze.orderby
i zostałem śledzony, szukając go :)Odpowiedzi:
Spróbuj umieścić obie kolumny w tej samej kolejności
W przeciwnym razie każde zlecenie jest osobną operacją na kolekcji, za każdym razem zmieniając jego kolejność.
Powinno to uporządkować najpierw te, które mają wartość, a następnie kolejność wartości.
źródło
orderby p.LowestPrice == null, p.LowestPrice ascending
Nadzieja pomaga komuś.Naprawdę pomaga zrozumieć składnię zapytania LINQ i sposób jej tłumaczenia na wywołania metod LINQ.
Okazało się, że
zostaną przetłumaczone przez kompilator na
To zdecydowanie nie jest to, czego chcesz. Te rodzaje by
Product.LowestPrice.HasValue
wdescending
kolejności, a następnie ponownie sortuje przez całą kolekcjęProduct.LowestPrice
wdescending
porządku.To czego chcesz
które można uzyskać za pomocą składni zapytania
Aby uzyskać szczegółowe informacje na temat tłumaczenia składni zapytania na wywołania metod, zobacz specyfikację języka. Poważnie. Przeczytaj to.
źródło
Rozwiązanie dla wartości łańcuchowych jest naprawdę dziwne:
Jedynym powodem, dla którego to działa, jest to, że pierwsze wyrażenie
OrderBy()
,, sortujebool
wartości:true
/false
.false
wynik najpierw przejdź dotrue
wyniku (ThenBy()
wartości null ) i sortuj wartości niezerowe w kolejności alfabetycznej.Dlatego wolę zrobić coś bardziej czytelnego, takiego jak to:
Jeśli
SomeString
jest null, zostanie zastąpiony przez"z"
a następnie posortowany alfabetycznie.UWAGA: To nie jest ostateczne rozwiązanie, ponieważ
"z"
jest pierwsze niż wartości z, takie jakzebra
.UPDATE 9/6/2016 - O komentarzu @jornhd, jest to naprawdę dobre rozwiązanie, ale wciąż jest trochę skomplikowane, więc zalecę zawinięcie go w klasę rozszerzenia, taką jak ta:
I po prostu użyj go jak:
źródło
Mam inną opcję w tej sytuacji. Moja lista to objList i muszę zamówić, ale wartości null muszą być na końcu. moja decyzja:
źródło
Próbowałem znaleźć rozwiązanie LINQ, ale nie mogłem tego rozwiązać na podstawie odpowiedzi tutaj.
Moja ostateczna odpowiedź brzmiała:
źródło
moja decyzja:
źródło
Oto, co wymyśliłem, ponieważ używam metod rozszerzających, a mój element jest ciągiem, więc nie
.HasValue
:Działa to z obiektami LINQ 2 w pamięci. Nie testowałem tego z EF ani żadnym DB ORM.
źródło
Poniżej znajduje się metoda rozszerzenia do sprawdzania wartości null, jeśli chcesz posortować według właściwości podrzędnej keySelector.
I po prostu użyj go jak:
źródło
Oto inny sposób:
SUP_APPROVED_IND is char(1) in Oracle db.
Zauważ, że
r.SUP_APPROVED_IND.Trim() == null
jest traktowany jakotrim(SUP_APPROVED_IND) is null
w bazie danych Oracle.Zobacz to, aby uzyskać szczegółowe informacje: Jak mogę wysyłać zapytania o wartości null w ramach jednostki?
źródło
Inna opcja (była przydatna w naszym scenariuszu):
Mamy tabelę użytkowników, przechowującą
ADName, LastName, FirstName
Zmieniliśmy schemat tabeli i dodaliśmy kolumnę „SortIndex”, która definiuje niektóre grupy sortowania. (Pozostawiliśmy odstęp 5, więc możemy wstawić grupy później)
Teraz, pod względem zapytania, byłoby to:
w wyrażeniach metod:
co daje oczekiwany wynik:
źródło