Powiedzmy, że mam 3 ciągi na liście (np. „1”, „2”, „3”).
Następnie chcę zmienić ich kolejność, aby umieścić „2” w pozycji 1 (np. „2”, „1”, „3”).
Korzystam z tego kodu (ustawiam indexToMoveTo na 1):
listInstance.Remove(itemToMove);
listInstance.Insert(indexToMoveTo, itemToMove);
To wydaje się działać, ale czasami uzyskuję dziwne wyniki; czasami zamówienie jest nieprawidłowe lub elementy z listy są usuwane!
Jakieś pomysły? Czy List<T>
zamówienie gwarancyjne?
Związane z:
Czy lista <T> gwarantuje, że przedmioty zostaną zwrócone w kolejności, w jakiej zostały dodane?
c#
.net
collections
SuperSuperDev1234
źródło
źródło
Odpowiedzi:
List<>
Klasa nie gwarantuje uporządkowanie - rzeczy zostaną zachowane na liście w kolejności ich dodawania, włączając duplikatów, chyba że jawnie sortowania listy.Według MSDN:
Wartości indeksu muszą pozostać wiarygodne, aby były dokładne. Dlatego zamówienie jest gwarantowane.
Możesz uzyskać dziwne wyniki z kodu, jeśli przenosisz element później na liście, ponieważ
Remove()
przeniesiesz wszystkie inne elementy w dół o jedno miejsce przed wezwaniem doInsert()
.Czy potrafisz sprowadzić swój kod do czegoś wystarczająco małego, aby go opublikować?
źródło
List
w dowolnym dobrym podręczniku informatyki. Podobnie jakQueue
iStack
, aList
jest dobrze zdefiniowaną, przewidywalną i dobrze zrozumiałą strukturą danych - jeśli implementacja .NET będzie się różnić (lub jeśli się zmieni), wiele programów ulegnie awarii.Where()
metody LINQ do filtrowania listy, polegasz na implementacji, aby rozważyć kolejno pozycje w sekwencji. Zdarza się, że tak (zob. Referenceource.microsoft.com/System.Core/System/Linq/... ), ale nie jest to udokumentowane w MSDN. Sugerowałbym użycie,emp.LastOrDefault(x => x.empDept = 'abc')
ponieważ dokumentacjaLastOrDefault()
wskazuje, że zachowuje kolejność elementów.Oto 4 elementy z ich indeksem
Chcesz przenieść K pomiędzy A i E - możesz pomyśleć o pozycji 3. Uważaj tutaj na swoje indeksowanie, ponieważ po usunięciu wszystkie indeksy są aktualizowane.
Więc najpierw usuwasz element 0, pozostawiając
Następnie wstawiasz o 3
Aby uzyskać poprawny wynik, powinieneś użyć indeksu 2. Aby zachować spójność, musisz wysłać do (indexToMoveTo-1)
if indexToMoveTo > indexToMove
, np.Może to być związane z twoim problemem. Uwaga: mój kod nie został przetestowany!
EDYCJA : Alternatywnie możesz
Sort
użyć niestandardowego modułu porównującego (IComparer
), jeśli dotyczy to twojej sytuacji.źródło
Jak powiedział Bevan, pamiętaj jednak, że indeks listy jest oparty na 0. Jeśli chcesz przenieść element na początek listy, musisz wstawić go pod indeksem 0 (nie 1, jak pokazano w twoim przykładzie).
źródło
Oto kod do przesunięcia elementu o jedno miejsce w dół na liście:
i to za przeniesienie go o jedno miejsce w górę:
folderImages
jestListBox
oczywiście, więc listaListBox.ObjectCollection
nie jestList<T>
, ale dziedziczy poIList
niej, więc powinna zachowywać się tak samo. czy to pomaga?Oczywiście ten pierwszy działa tylko wtedy, gdy wybrany element nie jest ostatnim elementem na liście, a drugi, jeśli wybrany element nie jest pierwszym elementem.
źródło
Jeśli zmienisz kolejność operacji, unikniesz dziwnego zachowania: Najpierw wstaw wartość we właściwe miejsce na liście, a następnie usuń ją z jego pierwszej pozycji. Pamiętaj, aby usunąć go według jego indeksu, ponieważ jeśli usuniesz go przez odniesienie, możesz usunąć je oba ...
źródło