Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Struct v/s Class in C# - Please explain the behavior

Could someone please explain the behavior of this

  class testCompile
    {
       /*
        *   Sample Code For Purpose of Illustration
        */
       struct person 
       {
           public int age;
           public string name;

       }

        static void Main(string[] args)
        {
            List<person> Listperson = new List<person>();
            person myperson = new person();

            for (int i = 1; i <= 2; i++)
            { 
                //Assignment
                myperson.age = 22+i;
                myperson.name = "Person - " + i.ToString();
                Listperson.Add(myperson);
            }
            int x = 0;
            while (x < Listperson.Count)
            {
                //Output values
                Console.WriteLine("{0} - {1}", Listperson[x].name, Listperson[x].age);
                x++;
            }
        }
    }

/*  
    Output:
    Person - 1 - 23
    Person - 2 - 24
*/

Why am I not getting the same output for a class as that of a struct?

class testCompile
    {
       /*
        *   Sample Code For Purpose of Illustration
        */
       class person 
       {
           public int age;
           public string name;

       }

        static void Main(string[] args)
        {
            List<person> Listperson = new List<person>();
            person myperson = new person();

            for (int i = 1; i <= 2; i++)
            { 
                //Assignment
                myperson.age = 22+i;
                myperson.name = "Person - " + i.ToString();
                Listperson.Add(myperson);
            }
            int x = 0;
            while (x < Listperson.Count)
            {
                //Output values
                Console.WriteLine("{0} - {1}", Listperson[x].name, Listperson[x].age);
                x++;
            }
        }
    }
/*  
    Output:
    Person - 2 - 24
    Person - 2 - 24 
*/
like image 565
abhi Avatar asked Oct 13 '10 13:10

abhi


3 Answers

Classes are reference types, structs are value types.

When a value type is passed to a method as a parameter, a copy of it will be passed through. That means that you add two completely separate copies of the Person struct, one for each pass in the loop.

When a reference type is passed to a method as a parameter, the reference will be passed through. That mean that you add two copies of the reference to the same memory location (to the same Person object) - when making changes to this one object, you see it reflected in both references since they both reference the same object.

like image 175
Oded Avatar answered Sep 21 '22 00:09

Oded


It's the difference between value type (struct) and reference type (class).

  • When you're adding the struct to Listperson the content of person is put in the list, you have two different person struct in your list.

    for (int i = 1; i <= 2; i++)
    { 
      //Assignment
      myperson.age = 22+i;
      myperson.name = "Person - " + i.ToString();
      Listperson.Add(myperson);
      /* First time: 
         Listperson contains a person struct with value { age = 23, name = 1}
         Second iteration:
         Listperson contains a person struct with value { age = 23, name = 1}
         Listperson contains another person struct with value { age = 24, name = 2} 
      */
    }
    
  • When you're adding the class the reference is put in the list, you have two references that referenced the same person object.

    for (int i = 1; i <= 2; i++)
    { 
      //Assignment
      myperson.age = 22+i;
      myperson.name = "Person - " + i.ToString();
      Listperson.Add(myperson);
      /* First time: 
         Listperson contains 1 reference to myperson object with value { age = 23, name = 1}
         Second iteration:
         Listperson contains 2 reference to myperson object with value { age = 24, name = 2} 
      */
    }
    
like image 39
Julien Hoarau Avatar answered Sep 22 '22 00:09

Julien Hoarau


Because your myperson variable only ever deals with one person struct/class.

What you add to the list, in your loop, is a copy of your myperson variable - which for the struct, will be an entire copy of the struct, but for the class will be a copy of the reference to the single instance that you create (and mutate).

like image 24
Damien_The_Unbeliever Avatar answered Sep 21 '22 00:09

Damien_The_Unbeliever