none
why compiler error re: method GetEnumerator() not in context RRS feed

  • Question

  • I typed the following code verbatim from the documents at IEnumberator but I get a compiler error at line 40 stating "Name GetEnumerator does not exist in the current context". I have seen this error when I forget to extend the right interface, and I think I have done that. Can someone have a look and see if they can figure out why I get this error? 
    using System;
    using System.Collections;
    
    namespace EnumeratorExample
    {
        class Program
        {
            static void Main(string[] args)
            {
                Console.WriteLine("Hello World!");
            }
        }
        public class Person
        {
            public Person(string fName, string lName)
            {
                this.firstName = fName;
                this.lastName = lName;
            }
            public string firstName;
            public string lastName;
        }
        public class People : IEnumerable
        {
            private Person[] _people;
    
            People(Person[] pArray)
            {
                //I am going to try this and see what it gives me 
                //this._people = pArray;
    
                _people = new Person[pArray.Length];
                for (int i = 0; i < pArray.Length; i++)
                {
                    _people[i] = pArray[i];
                }
            }
            IEnumerator IEnumerable.GetEnumerator()
            {
                return (IEnumerator) GetEnumerator();
            }
            public PeopleEnum GetEnumertor()
            {
                return new PeopleEnum(_people);
            }
            //When you implement IEnumerable you must also implement IEnumerator
        
        }
        public class PeopleEnum: IEnumerator
        {
            public Person[] _people;
    
            int position = -1;
            public PeopleEnum(Person[] list)
            {
                _people = list;
            }
            object IEnumerator.Current {
                get
                {
                    return Current;
                }
            }
            public Person Current
            {
                get
                {
                    try
                    {
                        return _people[position];
                    }
                    catch(IndexOutOfRangeException)
                    {
                        throw new InvalidOperationException();
                    }
                }
            }
    
            public bool MoveNext()
            {
                position++;
                return (position < _people.Length);
            }
    
            public void Reset()
            {
                position = -1;
            }
        }
        
    }

    Monday, June 3, 2019 8:10 AM

Answers

  • Two errors in your code:

    1) the People constructor has to be public

    public People(Person[] pArray)
            {
                //I am going to try this and see what it gives me 
                //this._people = pArray;
    
                _people = new Person[pArray.Length];
                for (int i = 0; i < pArray.Length; i++)
                {
                    _people[i] = pArray[i];
                }
            }
    2) It has to be "GetEnumerator" not "GetEnumertor":
    public PeopleEnum GetEnumerator()
            {
                return new PeopleEnum(_people);
            }

    To see how it actually works, you should put something useful into your main method:

    static void Main(string[] args)
    {
        People peoples = new People(new Person[]
        {
            new Person("Donald", "Duck"),
            new Person("Micky", "Mouse"),
            new Person("Daisy", "Duck"),
            new Person("Scrooge", "McDuck")
        });
        foreach (Person p in peoples)
            Console.WriteLine(p.firstName + " " + p.lastName);
    
        Console.WriteLine("\nPress any key to continue.");
        Console.ReadLine();
    }

    wizend


    • Edited by Wizend Monday, June 3, 2019 10:38 AM main method
    • Marked as answer by Nu2Csharp Monday, June 3, 2019 7:24 PM
    Monday, June 3, 2019 10:15 AM

All replies

  • Hi Nu,

    Welcome to the MSDN forum.

    Based on your description, it is related to c# compiler issue. Since our forum mainly focus on VS setup, I will help you move it to an appropriate forum.

    Thank you for your understanding.

    Sincerely

    May


    MSDN Community Support Please remember to click "Mark as Answer" the responses that resolved your issue, and to click "Unmark as Answer" if not. This can be beneficial to other community members reading this thread. If you have any compliments or complaints to MSDN Support, feel free to contact MSDNFSF@microsoft.com

    Monday, June 3, 2019 9:21 AM
  • See if this fixes the problem.

    using System;
    using System.Collections;
    
    namespace EnumeratorExample
    {
        class Program
        {
            static void Main(string[] args)
            {
                Console.WriteLine("Hello World!");
            }
        }
        public class Person
        {
            public Person(string fName, string lName)
            {
                this.firstName = fName;
                this.lastName = lName;
            }
            public string firstName;
            public string lastName;
        }
        public class People : IEnumerable
        {
            private Person[] _people;
    
            People(Person[] pArray)
            {
                //I am going to try this and see what it gives me 
                //this._people = pArray;
    
                _people = new Person[pArray.Length];
                for (int i = 0; i < pArray.Length; i++)
                {
                    _people[i] = pArray[i];
                }
            }
            IEnumerator IEnumerable.GetEnumerator()
            {
                return (IEnumerator)GetEnumertor();
            }
            public PeopleEnum GetEnumertor()
            {
                return new PeopleEnum(_people);
            }
            //When you implement IEnumerable you must also implement IEnumerator
    
        }
        public class PeopleEnum : IEnumerator
        {
            public Person[] _people;
    
            int position = -1;
            public PeopleEnum(Person[] list)
            {
                _people = list;
            }
            object IEnumerator.Current
            {
                get
                {
                    return Current;
                }
            }
            public Person Current
            {
                get
                {
                    try
                    {
                        return _people[position];
                    }
                    catch (IndexOutOfRangeException)
                    {
                        throw new InvalidOperationException();
                    }
                }
            }
    
            public bool MoveNext()
            {
                position++;
                return (position < _people.Length);
            }
    
            public void Reset()
            {
                position = -1;
            }
        }
    
    }
    


    Please remember to mark the replies as answers if they help and unmarked them if they provide no help, this will help others who are looking for solutions to the same or similar problem. Contact via my Twitter (Karen Payne) or Facebook (Karen Payne) via my MSDN profile but will not answer coding question on either.

    NuGet BaseConnectionLibrary for database connections.

    StackOverFlow
    profile for Karen Payne on Stack Exchange

    Monday, June 3, 2019 9:54 AM
    Moderator
  • Two errors in your code:

    1) the People constructor has to be public

    public People(Person[] pArray)
            {
                //I am going to try this and see what it gives me 
                //this._people = pArray;
    
                _people = new Person[pArray.Length];
                for (int i = 0; i < pArray.Length; i++)
                {
                    _people[i] = pArray[i];
                }
            }
    2) It has to be "GetEnumerator" not "GetEnumertor":
    public PeopleEnum GetEnumerator()
            {
                return new PeopleEnum(_people);
            }

    To see how it actually works, you should put something useful into your main method:

    static void Main(string[] args)
    {
        People peoples = new People(new Person[]
        {
            new Person("Donald", "Duck"),
            new Person("Micky", "Mouse"),
            new Person("Daisy", "Duck"),
            new Person("Scrooge", "McDuck")
        });
        foreach (Person p in peoples)
            Console.WriteLine(p.firstName + " " + p.lastName);
    
        Console.WriteLine("\nPress any key to continue.");
        Console.ReadLine();
    }

    wizend


    • Edited by Wizend Monday, June 3, 2019 10:38 AM main method
    • Marked as answer by Nu2Csharp Monday, June 3, 2019 7:24 PM
    Monday, June 3, 2019 10:15 AM
  • Thank you so much. I am not sure if I can ask one more question about the code above. Do you know why they implemented the People constructor by setting each value of the arrays equal to each other and ensuring that the size of the arrays were the same, but in the case of PeopleEnum they just say _people=list as follows: 

    Public People (Person [] pArray){

    _people = new Person[pArray.lenght];

    for (i=0; i<pArray.lenght; i++){

    _people[i]=pArray[i];

    }

    ************

    in PeopleEnum class they say 

    Public PeopleEnum(Person[] list){

    _people = list;

    }

    My question is why are they treating array equality different; they are doing the same task of instantiating an instance of a class that is basically an array of other objects. 

    • Edited by Nu2Csharp Monday, June 3, 2019 10:25 PM
    Monday, June 3, 2019 10:24 PM
  • In your People constructor you make a memberwise copy of the original array, because arrays are derived from System.Object and so they are always - regardless of their content - reference types. That means, if you would simply assign your original People array to the field _people of your People class, like:

    public People(Person[] pArray)
    {
        _people = pArray;
    }
    then your _people variable would be like a pointer to your original pArray. Your new People object and your original one would be coupled. It might not affect the functionality of this much simplified code sample. But in most real-life scenarios such a result might not be welcomed.

    The assignment in the subclass PeopleEnum is different because it belongs to the internal logic of your People class. So, to set a reference to the Person[] _people is even required to make the whole thing work.

    wizend

    Tuesday, June 4, 2019 9:43 AM
  • Thank you so much. So is it correct to say that I will learn to anticipate when I want two different copies of an array vs. using the same array with two different pointers. I say this because as far as I know the normal array implementation is basically a pointer of the first element of it. Not sure if you agree.

    Tuesday, June 4, 2019 2:46 PM
  • A basic understanding of the difference between reference types and value types is fundamental. After reading your last post I'm afraid my attempt of explaining it to you was more confusing than helpful.

    So, I found this article References and Values written by Jon Skeet, who has not only profound insight into this topic but also the necessary skills to explain it so that even someone with no IT background at all will be able to get a grip on it. 

    I hope, it will help you,

    wizend

    Tuesday, June 4, 2019 3:21 PM
  • Thanks. I read the content, and I believe I see why you shared the link. I'll follow up with the author to validate. I am very appreciative of you taking the time to further assist. 
    Tuesday, June 4, 2019 8:39 PM