Frage

Ich habe diesen Code (C #):

using System.Collections.Generic;

namespace ConsoleApplication1
{
    public struct Thing
    {
        public string Name;
    }

    class Program
    {
        static void Main(string[] args)
        {
            List<Thing> things = new List<Thing>();
            foreach (Thing t in things) //  for each file
            {
                t.Name = "xxx";
            }
        }
    }
}

Es wird nicht kompilieren.
Der Fehler ist:

Cannot modify members of 't' because it is a 'foreach iteration variable'

Wenn ich Thing auf einen class eher als ein struct ändern, jedoch ist es kompilieren.

Bitte kann mir jemand erklären, was los ist?

War es hilfreich?

Lösung

Mehr oder weniger, was er sagt, wird der Compiler können Sie nicht (oder Teile davon) stell den Looping var in einer foreach.

Verwenden Sie einfach:

for(int i = 0; i < things.Count; i+= 1) //  for each file
{
    things[i].Name = "xxx";
}

Und es funktioniert, wenn Thing eine Klasse ist, weil dann Looping var eine Referenz ist, und Sie nur Änderungen auf das referenzierte Objekt machen, nicht auf die Referenz selbst.

Andere Tipps

Eine Struktur ist kein Referenztyp, sondern ein Werttyp.

Wenn Sie eine class anstelle eines struct für Thing hätte, würde die foreach-Schleife eine Referenzgröße für Sie erstellen, die auf das richtige Element zeigen würde Sie aufzulisten. Aber da es sich um ein Werttyp ist, es funktioniert nur auf einer Kopie Ihres Thing, die in diesem Fall ist die Iterationsvariable.

Eine Struktur ist ein Werttyp, sondern eine Klasse ist ein Referenztyp. Deshalb ist es kompiliert, wenn diese eine Klasse ist, aber nicht, wenn es sich um eine Struktur

Sehen Sie mehr: http://www.albahari.com/valuevsreftypes.aspx

Eine alternative Syntax, die ich lieber @ Henk-Lösung das ist.

DateTime[] dates = new DateTime[10];

foreach(int index in Enumerable.Range(0, dates.Length))
{
   ref DateTime date = ref dates[index];

   // Do stuff with date.
   // ...
}

Wenn Sie eine angemessene Menge an Arbeit in der Schleife zu tun haben dann nicht die Indizierung überall zu wiederholen ist einfacher auf dem Auge imo.

P. S. Datetime ist eigentlich ein wirklich schlechtes Beispiel, da es keine Eigenschaften aufweist, die Sie festlegen können, aber Sie erhalten das Bild.

Lizenziert unter: CC-BY-SA mit Zuschreibung
Nicht verbunden mit StackOverflow
scroll top