Uwielbiam string.IsNullOrEmpty
metodę. Chciałbym mieć coś, co zapewniłoby tę samą funkcjonalność dla IEnumerable. Czy jest taki? Może jakaś klasa pomocnika kolekcji? Powodem, o który pytam, jest to, że w if
instrukcjach kod wygląda na zagracony, jeśli wzór jest (mylist != null && mylist.Any())
. Byłoby o wiele czystsze Foo.IsAny(myList)
.
Ten post nie daje takiej odpowiedzi: IEnumerable jest puste? .
c#
.net
linq
collections
ienumerable
Schultz9999
źródło
źródło
Odpowiedzi:
Jasne, że mógłbyś napisać:
należy jednak uważać, aby nie wszystkie sekwencje były powtarzalne; generalnie wolę spacerować tylko raz, na wszelki wypadek.
źródło
this
- uważam metody rozszerzające, które są przypuszczalnie wywoływanenull
jako oznaka brzydkiego projektu..Any()
to metoda rozszerzająca, która działa naIEnumerable<T>
(lubIQueryable<T>
, chociaż to inny scenariusz). Robi to , przynajmniej częściowo, zużywa sekwencję (chociaż nadal oznacza to, że jest zużyta) - może być konieczne odczytanie tylko jednego elementu (zwłaszcza jeśli nie ma predykatu). Jako takie, ponieważ sekwencje (IEnumerable<T>
) nie muszą być powtarzalne, to może być to .Any()
bez predykatu jest zasadniczo równoważneforeach(var x in sequence) { return true; } return false;
- chociaż używaGetEnumerator()
etc zamiast składni kompilatoraźródło
IEnumerable
nie maAny()
rozszerzenia.Oto zmodyfikowana wersja przydatnej odpowiedzi @Matt Greer, która zawiera statyczną klasę opakowującą, więc możesz ją po prostu skopiować i wkleić do nowego pliku źródłowego, nie zależy od Linq i dodaje ogólne
IEnumerable<T>
przeciążenie, aby uniknąć pakowania typów wartości co by się zdarzyło w przypadku wersji innej niż ogólna. [EDYTUJ: Zauważ, że użycieIEnumerable<T>
nie zapobiega pudełkowaniu modułu wyliczającego, pisanie kaczkami nie może temu zapobiec, ale przynajmniej elementy w kolekcji o typie wartości nie będą każdy z nich.]źródło
Innym sposobem byłoby pobranie modułu Enumerator i wywołanie metody MoveNext (), aby sprawdzić, czy są jakieś elementy:
Działa to zarówno dla IEnumerable, jak i IEnumerable <T>.
źródło
IEnumerable<T>
, ponieważ nieogólneIEnumerable
nie implementujeIDisposable
.Sposób, w jaki to robię, wykorzystując kilka nowoczesnych funkcji C #:
Opcja 1)
Opcja 2)
A tak przy okazji, nigdy nie używaj
Count == 0
lubCount() == 0
po prostu sprawdzaj, czy kolekcja jest pusta. Zawsze używaj Linq's.Any()
źródło
!
może być operator negacji , szczególnie w drugiej opcji;)To może pomóc
źródło
Począwszy od C # 6 możesz użyć propagacji wartości null :
myList?.Any() == true
Jeśli nadal uważasz, że jest to zbyt zatkane lub wolisz starą dobrą metodę rozszerzenia, polecam odpowiedzi Matta Greera i Marca Gravella, ale z odrobiną rozszerzonej funkcjonalności dla kompletności.
Ich odpowiedzi zapewniają tę samą podstawową funkcjonalność, ale każda z innej perspektywy. Odpowiedź Matta wykorzystuje
string.IsNullOrEmpty
mentalność, podczas gdy odpowiedź Marca prowadzi Linqa.Any()
do wykonania zadania.Osobiście jestem skłonny do korzystania z
.Any()
drogi, ale chciałbym dodać funkcję sprawdzania stanu z innego przeciążenia metody :Więc nadal możesz robić takie rzeczy, jak:
myList.AnyNotNull(item=>item.AnswerToLife == 42);
tak jak w przypadku zwykłego,.Any()
ale z dodanym sprawdzaniem zerowymZwróć uwagę, że w C # 6 sposób:
myList?.Any()
zwraca abool?
zamiast abool
, co jest rzeczywistym efektem propagacji nullźródło
źródło
Oto kod z odpowiedzi Marca Gravella wraz z przykładem jego użycia.
Jak mówi, nie wszystkie sekwencje są powtarzalne, więc kod może czasami powodować problemy, ponieważ
IsAny()
zaczyna przechodzić przez sekwencję. Podejrzewam, że odpowiedź Roberta Harveya oznaczała, że często nie trzeba sprawdzaćnull
i opróżniać. Często wystarczy sprawdzić wartość null, a następnie użyćforeach
.Aby uniknąć dwukrotnego uruchamiania sekwencji i skorzystać z tego
foreach
, po prostu napisałem kod podobny do tego:Wydaje mi się, że metoda rozszerzenia pozwala zaoszczędzić kilka wierszy pisania, ale ten kod wydaje mi się bardziej przejrzysty. Podejrzewam, że niektórzy programiści nie od razu zorientują się, że
IsAny(items)
faktycznie zaczną przechodzić przez sekwencję. (Oczywiście, jeśli używasz wielu sekwencji, szybko nauczysz się myśleć o tym, co przez nie przechodzi).źródło
używam
Bool IsCollectionNullOrEmpty = !(Collection?.Any()??false);
. Mam nadzieję że to pomoże.Awaria:
Collection?.Any()
zwróci,null
jeśli Collection jest null ifalse
jeśli Collection jest pusta.Collection?.Any()??false
poda nam,false
czy kolekcja jest pusta, afalse
jeśli kolekcja jestnull
.Uzupełnienie tego da nam
IsEmptyOrNull
.źródło
Anwser Jona Skeeta ( https://stackoverflow.com/a/28904021/8207463 ) ma dobre podejście przy użyciu metody rozszerzenia - Any () dla NULL i EMPTY. ALE zatwierdza właściciela pytań w przypadku NIE NULL. Dlatego ostrożnie zmień podejście Jona do walidacji AS NULL na:
NIE używaj (nie zweryfikuje JAKO NULL):
Możesz również w przypadku walidacji jako NIE NULL (NIE testowane jako przykład, ale bez błędu kompilatora) zrobić coś takiego, jak użycie predykatu:
https://referencesource.microsoft.com/#System.Core/System/Linq/Enumerable.cs,8788153112b7ffd0
Dla której wersji .NET możesz go używać, sprawdź:
https://docs.microsoft.com/en-us/dotnet/api/system.linq.enumerable.any?view=netframework-4.8#moniker-applies-to
źródło
Miałem ten sam problem i rozwiązuję go tak:
„c => c! = null” zignoruje wszystkie puste jednostki.
źródło
Zbudowałem to na podstawie odpowiedzi @Matt Greer
Doskonale odpowiedział na pytanie OP.
Chciałem coś takiego, zachowując oryginalne możliwości Any, jednocześnie sprawdzając, czy nie ma wartości null. Publikuję to na wypadek, gdyby ktoś inny potrzebował czegoś podobnego.
W szczególności chciałem nadal móc przekazać predykat.
Nazewnictwo metody rozszerzenia mogłoby być prawdopodobnie lepsze.
źródło
Inne najlepsze rozwiązanie, jak poniżej, aby sprawdzić, czy jest puste, czy nie?
źródło
listEnumerable
jest zerowe, co jest pytaniem pod rękąUżywam tego:
Ejem:
źródło
Ponieważ niektóre zasoby wyczerpują się po jednym czytaniu, pomyślałem, dlaczego nie połączyć sprawdzeń i odczytów zamiast tradycyjnego oddzielnego sprawdzenia, a następnie przeczytać.
Najpierw mamy jedno dla prostszego rozszerzenia wbudowanego check-for-null:
Następnie mamy trochę bardziej zaangażowane (cóż, przynajmniej tak, jak to napisałem) rozszerzenie wbudowane check-for-null-and-empty:
Oczywiście możesz nadal dzwonić do obu bez kontynuowania łańcucha połączeń. Dołączyłem również parametr paramName, aby wywołujący mógł podać alternatywną nazwę błędu, jeśli nie jest sprawdzane „źródło”, np. „Nameof (target)”.
źródło
moja własna metoda rozszerzenia, aby sprawdzić Not null i Any
źródło
Bez niestandardowych pomocników polecam albo
?.Any() ?? false
lub?.Any() == true
które są stosunkowo zwięzły i tylko trzeba określić sekwencję raz.Kiedy chcę traktować brakującą kolekcję jak pustą, używam następującej metody rozszerzenia:
Tę funkcję można łączyć ze wszystkimi metodami LINQ i
foreach
nie tylko.Any()
, dlatego wolę ją od bardziej wyspecjalizowanych funkcji pomocniczych, które ludzie tutaj proponują.źródło
używam
Wynik będzie pusty, jeśli brak dopasowania, w przeciwnym razie zwraca jeden z obiektów
Jeśli chcesz mieć listę, myślę, że opuszczenie First () lub wywołanie ToList () dostarczy listę lub wartość null.
źródło
Spójrz na tę bibliotekę open source: Nzr.ToolBox
źródło
po prostu dodaj
using System.Linq
i zobacz magię, która dzieje się, gdy próbujesz uzyskać dostęp do dostępnych metod wIEnumerable
. Dodanie tego da ci dostęp do metody oCount()
tak prostej nazwie . pamiętaj tylko, aby sprawdzićnull value
przed zadzwonieniemcount()
:)źródło
Użyłem prostego, jeśli to sprawdzić
sprawdź moje rozwiązanie
źródło