Sobes.tech
Junior

Τι τύποι αντικειμένων μπορούν να χρησιμοποιηθούν σε ένα βρόχο foreach σε C#;

sobes.tech AI

Απάντηση από AI

Στον βρόχο foreach στη C# μπορούν να χρησιμοποιηθούν οποιοδήποτε είδη αντικειμένων που υλοποιούν μία από τις ακόλουθες διεπαφές:

  • System.Collections.IEnumerable - Για μη γενικές συλλογές. Παρέχει έναν μη γενικό επαναληπτή IEnumerator.
  • System.Collections.Generic.IEnumerable<T> - Για γενικές συλλογές. Παρέχει έναν γενικό επαναληπτή IEnumerator<T>.

Μια κλάση ή δομή μπορεί επίσης να χρησιμοποιηθεί στο foreach εάν διαθέτει μια δημόσια μέθοδο GetEnumerator(), η οποία επιστρέφει ένα στιγμιότυπο μιας κλάσης ή δομής που υλοποιεί την ακόλουθη υπογραφή (αυτό ονομάζεται foreach βασισμένο σε μοτίβο):

  • Δημόσια ιδιότητα Current, που επιστρέφει οποιοδήποτε τύπο.
  • Δημόσια μέθοδο MoveNext(), που επιστρέφει bool.
  • Προαιρετικά, δημόσια μέθοδο Dispose() (για σωστό απελευθέρωση πόρων κατά τη χρήση using).

Παραδείγματα ενσωματωμένων τύπων που μπορούν να χρησιμοποιηθούν:

  • Πίνακες (int[], string[], κ.λπ.)
  • Συλλογές από το χώρο ονομάτων System.Collections: ArrayList, Hashtable, Queue, Stack.
  • Συλλογές από το χώρο ονομάτων System.Collections.Generic: List<T>, Dictionary<TKey, TValue>, HashSet<T>, Queue<T>, Stack<T>.
  • Strings (string) - που αποτελούνται από ακολουθίες χαρακτήρων char.

Παράδειγμα προσαρμοσμένου τύπου που υποστηρίζει foreach σύμφωνα με το μοτίβο:

// Απλός προσαρμοσμένος τύπος που υποστηρίζει foreach
public class MyEnumerable
{
    private int[] data = { 1, 2, 3, 4, 5 };

    // Μέθοδος GetEnumerator που υποστηρίζει foreach σύμφωνα με το μοτίβο
    public MyEnumerator GetEnumerator()
    {
        return new MyEnumerator(data);
    }

    // Εσωτερική κλάση του enumerator
    public class MyEnumerator
    {
        private int[] data;
        private int currentIndex = -1;

        public MyEnumerator(int[] data)
        {
            this.data = data;
        }

        // Ιδιότητα Current
        public int Current => data[currentIndex];

        // Μέθοδος MoveNext
        public bool MoveNext()
        {
            currentIndex++;
            return currentIndex < data.Length;
        }

        // Μέθοδος Dispose (προαιρετικά)
        public void Dispose()
        {
            // Απελευθέρωση πόρων αν χρειάζεται
        }
    }
}

// Χρήση σε `foreach`
// var collection = new MyEnumerable();
// foreach (var item in collection)
// {
//     // Console.WriteLine(item);
// }