GetEnumerator

  • VB.NET

Es gibt 11 Antworten in diesem Thema. Der letzte Beitrag () ist von RodFromGermany.

    GetEnumerator

    Hi Leute,
    ich habe eine Klasse, die eine List(Of T) enthält.
    Ich möchte diese Klasse bezüglich dieser Liste enumerierbar machen (For Each...)
    Als Beispiel dient die MSDN:IEnumerable
    Problem:

    VB.NET-Quellcode

    1. Public Class People
    2. Implements IEnumerable
    3. Public Function GetEnumerator() As IEnumerator Implements IEnumerable.GetEnumerator
    4. Return @@@
    5. End Function
    6. End Class
    Alles in Ordnung.

    VB.NET-Quellcode

    1. Public Class People
    2. Implements IEnumerable (Of Person)
    3. Public Function GetEnumerator() As IEnumerator Implements IEnumerable.GetEnumerator
    4. Return @@@
    5. End Function
    6. End Class
    bringt den Fehler
    Class "People" muss "Function GetEnumerator() As IEnumerator(Of WindowsApplication1.Person)" für die System.Collections.Generic.IEnumerable(Of Person)-Schnittstelle implementieren.

    VB.NET-Quellcode

    1. Public Class People
    2. Implements IEnumerable (Of Person)
    3. Function GetEnumerator() As IEnumerator(Of WindowsApplication1.Person) Implements IEnumerable(Of Person).GetEnumerator
    4. Return @@@
    5. End Function
    6. End Class
    bringt den Fehler
    Class "People" muss "Function GetEnumerator() As IEnumerator" für die System.Collections.IEnumerable-Schnittstelle implementieren.

    VB.NET-Quellcode

    1. Public Class People
    2. Implements IEnumerable (Of Person)
    3. Public Function GetEnumerator() As IEnumerator Implements IEnumerable.GetEnumerator
    4. Return @@@
    5. End Function
    6. Function GetEnumerator() As IEnumerator(Of WindowsApplication1.Person) Implements IEnumerable(Of Person).GetEnumerator
    7. Return @@@
    8. End Function
    9. End Class
    bringt den Fehler
    Public Function GetEnumerator() As System.Collections.IEnumerator" und "Public Function GetEnumerator() As System.Collections.Generic.IEnumerator(Of Person)" können sich nicht gegenseitig überladen, da sie sich nur durch Rückgabetypen unterscheiden.

    Hat jemand einen Tip für mich, wie das Interface Implements IEnumerable (Of Person) ordentlich zu implementieren ist?
    VS 2010, x64
    Danke.
    Falls Du diesen Code kopierst, achte auf die C&P-Bremse.
    Jede einzelne Zeile Deines Programms, die Du nicht explizit getestet hast, ist falsch :!:
    Ein guter .NET-Snippetkonverter (der ist verfügbar).
    Programmierfragen über PN / Konversation werden ignoriert!
    Hi Bernd,
    die Deklaration der Funktionen GetEnumerator() sind mein Problem, nicht der Inhalt.
    Falls Du diesen Code kopierst, achte auf die C&P-Bremse.
    Jede einzelne Zeile Deines Programms, die Du nicht explizit getestet hast, ist falsch :!:
    Ein guter .NET-Snippetkonverter (der ist verfügbar).
    Programmierfragen über PN / Konversation werden ignoriert!
    Anhand vom Beispiel von MSDN probiers mal so:

    VB.NET-Quellcode

    1. Public Class People
    2. Implements IEnumerable(Of Person)
    3. Public Function GetEnumerator() As IEnumerator Implements IEnumerable(Of Person).GetEnumerator
    4. Return New PeopleEnum(_people)
    5. End Function
    6. Private _people() As Person
    7. Public Sub New(ByVal pArray() As Person)
    8. _people = New Person(pArray.Length - 1) {}
    9. Dim i As Integer
    10. For i = 0 To pArray.Length - 1
    11. _people(i) = pArray(i)
    12. Next i
    13. End Sub
    14. Public Function GetEnumerator1() As System.Collections.Generic.IEnumerator(Of Person) Implements System.Collections.Generic.IEnumerable(Of Person).GetEnumerator
    15. Return New PeopleEnum(_people)
    16. End Function
    17. End Class


    Bringt bei mir zumindest keinen Fehler (kA bezüglich der Funktionalität)

    lg
    ScheduleLib 0.0.1.0
    Kleine Lib zum Anlaufen von Code zu bestimmten Zeiten
    @fichz: Das sieht sehr gut aus, funktioniert. :thumbsup:
    Hast Du mal fix die Seite parat, wo das steht? Ich suche nämlich noch das äquivalente C#-Beispiel.
    Die Auto-Übersetzung VB->C# funktioniert nämlich nicht.
    Falls Du diesen Code kopierst, achte auf die C&P-Bremse.
    Jede einzelne Zeile Deines Programms, die Du nicht explizit getestet hast, ist falsch :!:
    Ein guter .NET-Snippetkonverter (der ist verfügbar).
    Programmierfragen über PN / Konversation werden ignoriert!
    Muss ich leider passen.
    Ich hab jedeglich das Beispiel von MSDN koipert und das gemacht was die IDE als Fehler gekennzeichnet hat :/

    lg

    EDIT: Auf der MSDN gibt es das gleiche Beispiel in C#.
    Da ich leider C# (noch) nicht kann, kann ich dir aber leider nix dazu sagen :/
    Spoiler anzeigen

    Quellcode

    1. using System;
    2. using System.Collections;
    3. public class Person
    4. {
    5. public Person(string fName, string lName)
    6. {
    7. this.firstName = fName;
    8. this.lastName = lName;
    9. }
    10. public string firstName;
    11. public string lastName;
    12. }
    13. public class People : IEnumerable
    14. {
    15. private Person[] _people;
    16. public People(Person[] pArray)
    17. {
    18. _people = new Person[pArray.Length];
    19. for (int i = 0; i < pArray.Length; i++)
    20. {
    21. _people[i] = pArray[i];
    22. }
    23. }
    24. IEnumerator IEnumerable.GetEnumerator()
    25. {
    26. return (IEnumerator) GetEnumerator();
    27. }
    28. public PeopleEnum GetEnumerator()
    29. {
    30. return new PeopleEnum(_people);
    31. }
    32. }
    33. public class PeopleEnum : IEnumerator
    34. {
    35. public Person[] _people;
    36. // Enumerators are positioned before the first element
    37. // until the first MoveNext() call.
    38. int position = -1;
    39. public PeopleEnum(Person[] list)
    40. {
    41. _people = list;
    42. }
    43. public bool MoveNext()
    44. {
    45. position++;
    46. return (position < _people.Length);
    47. }
    48. public void Reset()
    49. {
    50. position = -1;
    51. }
    52. object IEnumerator.Current
    53. {
    54. get
    55. {
    56. return Current;
    57. }
    58. }
    59. public Person Current
    60. {
    61. get
    62. {
    63. try
    64. {
    65. return _people[position];
    66. }
    67. catch (IndexOutOfRangeException)
    68. {
    69. throw new InvalidOperationException();
    70. }
    71. }
    72. }
    73. }
    74. class App
    75. {
    76. static void Main()
    77. {
    78. Person[] peopleArray = new Person[3]
    79. {
    80. new Person("John", "Smith"),
    81. new Person("Jim", "Johnson"),
    82. new Person("Sue", "Rabon"),
    83. };
    84. People peopleList = new People(peopleArray);
    85. foreach (Person p in peopleList)
    86. Console.WriteLine(p.firstName + " " + p.lastName);
    87. }
    88. }
    89. /* This code produces output similar to the following:
    90. *
    91. * John Smith
    92. * Jim Johnson
    93. * Sue Rabon
    94. *
    95. */
    ScheduleLib 0.0.1.0
    Kleine Lib zum Anlaufen von Code zu bestimmten Zeiten

    Dieser Beitrag wurde bereits 1 mal editiert, zuletzt von „fichz“ ()

    ErfinderDesRades schrieb:

    welche Auto-Übersetzung? Online-Codeconverter macht kein Problem.
    Input VB:
    Spoiler anzeigen

    VB.NET-Quellcode

    1. Public Function GetEnumerator() As IEnumerator Implements IEnumerable(Of Person).GetEnumerator
    2. Return AllePersonen.GetEnumerator()
    3. End Function
    4. Public Function GetEnumerator1() As System.Collections.Generic.IEnumerator(Of Person) Implements System.Collections.Generic.IEnumerable(Of Person).GetEnumerator
    5. Return AllePersonen.GetEnumerator()
    6. End Function
    ist in Ordnung.
    Übersetzung nach C#:
    Spoiler anzeigen

    VB.NET-Quellcode

    1. public IEnumerator GetEnumerator()
    2. {
    3. return AllePersonen.GetEnumerator();
    4. }
    5. public System.Collections.Generic.IEnumerator<Person> GetEnumerator1()
    6. {
    7. return AllePersonen.GetEnumerator();
    8. }
    9. System.Collections.Generic.IEnumerator<Person> System.Collections.Generic.IEnumerable<Person>.GetEnumerator()
    10. {
    11. return GetEnumerator1();
    12. }
    bringt die Fehlermeldung
    Die Verwendung von Typ "System.Collections.Generic.IEnumerator<T>" (generisch) macht das 1-Typargument erforderlich.
    Falls Du diesen Code kopierst, achte auf die C&P-Bremse.
    Jede einzelne Zeile Deines Programms, die Du nicht explizit getestet hast, ist falsch :!:
    Ein guter .NET-Snippetkonverter (der ist verfügbar).
    Programmierfragen über PN / Konversation werden ignoriert!
    Bringt keinen Fehler:
    Spoiler anzeigen

    Quellcode

    1. using Microsoft.VisualBasic;
    2. using System;
    3. using System.Collections;
    4. using System.Collections.Generic;
    5. using System.Data;
    6. using System.Diagnostics;
    7. public class People : IEnumerable<Person>
    8. {
    9. public IEnumerator GetEnumerator()
    10. {
    11. return new PeopleEnum(_people);
    12. }
    13. private Person[] _people;
    14. public People(Person[] pArray)
    15. {
    16. _people = new Person[pArray.Length];
    17. int i = 0;
    18. for (i = 0; i <= pArray.Length - 1; i++) {
    19. _people[i] = pArray[i];
    20. }
    21. }
    22. public System.Collections.Generic.IEnumerator<Person> GetEnumerator1()
    23. {
    24. return new PeopleEnum(_people);
    25. }
    26. System.Collections.Generic.IEnumerator<Person> System.Collections.Generic.IEnumerable<Person>.GetEnumerator()
    27. {
    28. return GetEnumerator1();
    29. }
    30. }



    kA obs funzt^^

    lg
    ScheduleLib 0.0.1.0
    Kleine Lib zum Anlaufen von Code zu bestimmten Zeiten
    pech - mein c#-system ist down. aber im blindflug würdich vorschlagen, die 3.Methode rauszuwerfen - kapiernich, was die soll. Bleibt also

    Quellcode

    1. public IEnumerator GetEnumerator()
    2. {
    3. return AllePersonen.GetEnumerator();
    4. }
    5. public System.Collections.Generic.IEnumerator<Person> GetEnumerator1()
    6. {
    7. return AllePersonen.GetEnumerator();
    8. }
    Die Fehlermeldung macht mich vermuten, dass dein "AllePersonen" nicht IEnumerable<Person> implementiert

    ich würd übrigens ein kompakteres CodeLayout empfehlen - mit weniger (fast-)Leerzeilen und geringere einrücktiefe (man willja feste verschachteln ;)):

    Quellcode

    1. public IEnumerator GetEnumerator() {
    2. return AllePersonen.GetEnumerator();
    3. }
    4. public System.Collections.Generic.IEnumerator<Person> GetEnumerator1() {
    5. return AllePersonen.GetEnumerator();
    6. }
    Nimmt weniger Zeilen ein, und wird deutlicher, dasses 2 methoden sind, oder?
    Hab es auch gerade so gelöst.
    Beide Automaten haben 3 Prozeduren draus gemacht, die 1. ist einfach zu viel.

    Quellcode

    1. public System.Collections.Generic.IEnumerator<Person> GetEnumerator1()
    2. {
    3. return AllePersonen.GetEnumerator();
    4. }
    5. System.Collections.Generic.IEnumerator<Person> System.Collections.Generic.IEnumerable<Person>.GetEnumerator()
    6. {
    7. return GetEnumerator1();
    8. }
    Dein Layout ("{" am Ende der Zeile) widerspricht unseren firmeninternen Codierungsrichtlinien und meinem ästhetischen Empfinden. Das Klammer-Paar muss untereinander stehen. :rolleyes:

    Edit ---------------------------------------------------------------------------

    VB.NET-Quellcode

    1. For Each pp As Person In _Personen
    2. MessageBox.Show(pp.Name)
    3. Next
    funktioniert.

    Quellcode

    1. foreach (Person pp in _Personen)
    2. {
    3. MessageBox.Show(pp.Name);
    4. }
    bringt den Fehler
    "People" implementiert den Schnittstellenmember "System.Collections.IEnumerable.GetEnumerator()" nicht.
    "People.GetEnumerator()" hat nicht den entsprechenden Rückgabetyp "System.Collections.IEnumerator" und kann "System.Collections.IEnumerable.GetEnumerator()" daher nicht implementieren.
    Falls Du diesen Code kopierst, achte auf die C&P-Bremse.
    Jede einzelne Zeile Deines Programms, die Du nicht explizit getestet hast, ist falsch :!:
    Ein guter .NET-Snippetkonverter (der ist verfügbar).
    Programmierfragen über PN / Konversation werden ignoriert!

    Dieser Beitrag wurde bereits 1 mal editiert, zuletzt von „RodFromGermany“ () aus folgendem Grund: Zu früh gefreut, zurück zu Feld Nummer 1.

    Danke Euch beiden.
    Hat lange gedauert, aber jetzt hab ich es gefunden. :thumbsup: :thumbsup:
    Ursprünglich war nur

    Quellcode

    1. using System.Collections.Generic;
    eingefügt.
    Mit

    Quellcode

    1. using System.Collections;
    2. using System.Collections.Generic;
    3. public IEnumerator<Person> GetEnumerator()
    4. {
    5. return this.AllePersonen.GetEnumerator();
    6. }
    7. IEnumerator IEnumerable.GetEnumerator()
    8. {
    9. return this.GetEnumerator();
    10. }
    läuft es nun auch unter C#. :thumbup:
    Falls Du diesen Code kopierst, achte auf die C&P-Bremse.
    Jede einzelne Zeile Deines Programms, die Du nicht explizit getestet hast, ist falsch :!:
    Ein guter .NET-Snippetkonverter (der ist verfügbar).
    Programmierfragen über PN / Konversation werden ignoriert!