var ints = new List< int >( new[ ] {
1,
2,
3,
4,
5
} );
var first = true;
foreach( var v in ints ) {
if ( first ) {
for ( long i = 0 ; i < int.MaxValue ; ++i ) { //<-- The thing I iterate
ints.Add( 1 );
ints.RemoveAt( ints.Count - 1 );
}
ints.Add( 6 );
ints.Add( 7 );
}
Console.WriteLine( v );
first = false;
}
Wenn Sie die innere for
Schleife auskommentieren, wird sie ausgelöst, weil wir offensichtlich Änderungen an der Sammlung vorgenommen haben.
Wenn Sie es nun auskommentieren, warum können wir in dieser Schleife diese beiden Elemente hinzufügen? Es dauert eine Weile, bis es wie eine halbe Minute ausgeführt wird (auf Pentium-CPU), aber es wirft nicht, und das Lustige ist, dass es Folgendes ausgibt:
Es wurde ein bisschen erwartet, aber es zeigt an, dass wir uns ändern können und es ändert tatsächlich die Sammlung. Irgendwelche Ideen, warum dieses Verhalten auftritt?
c#
collections
LyingOnTheSky
quelle
quelle
int.MaxValue
Iterationen abgeschlossen sind ...Antworten:
Das Problem besteht darin, dass
List<T>
Änderungen erkannt werden, indem ein Versionsfeld vom Typint
beibehalten und bei jeder Änderung erhöht wird. Wenn Sie also zwischen den Iterationen genau ein Vielfaches von 2 32 Änderungen an der Liste vorgenommen haben, werden diese Änderungen für die Erkennung unsichtbar. (Es wird vonint.MaxValue
bis überlaufenint.MinValue
und schließlich zu seinem ursprünglichen Wert zurückkehren.)Wenn Sie so ziemlich alles an Ihrem Code ändern - fügen Sie 1 oder 3 Werte anstelle von 2 hinzu oder verringern Sie die Anzahl der Iterationen Ihrer inneren Schleife um 1, wird wie erwartet eine Ausnahme ausgelöst.
(Dies ist eher ein Implementierungsdetail als ein angegebenes Verhalten - und es ist ein Implementierungsdetail, das in einem sehr seltenen Fall als Fehler angesehen werden kann. Es wäre jedoch sehr ungewöhnlich, dass es in einem realen Programm ein Problem verursacht.)
quelle
_version
Feld ein istint
.InvalidOperationException
, was eigentlich nicht immer wahr ist. Dies hängt natürlich von der Definition des "Implementierungsdetails" ab.