1

I am new to developing and this is my first question, so please excuse any misunderstanding in my explanation.

I am trying to import the data from a csv file into a list of objects I defined. My file has 2 columns and 5 rows: 1 for the date and 1 for the volume of products sold that day. My application reads the file, store the data in 2 lists (1 for the date listDate, 1 for the volume of sale listVolume) then combines both data into a new object mySale and adds the object to the final list Car. It works fine as long as I add mySale to Car line by line (OPTION 1 in the code below) but when trying to use a loop (for statement), I always end up with my final list being populated with the last line of the file (OPTION 2 in the code below). During debug, I can see the properties date an volume are correct in mySale before adding it to Car but once the loop is finished, it seems the result has changed :-s I have the following code:

using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace dataManip
{
    class Program
    {

        static void Main(string[] args)
        {

            var reader = new StreamReader(File.OpenRead(@"C:\sales.csv"));
            List<DateTime> listDate = new List<DateTime>();
            List<int> listVolume = new List<int>();
            List<mySales> Car = new List<mySales>();

            while (!reader.EndOfStream)
            {
                var line = reader.ReadLine();
                var values = line.Split(',');

                listDate.Add(Convert.ToDateTime(values[0]));
                listVolume.Add(Convert.ToInt32(values[1]));
            }

            mySales mySale = new mySales();

            //OPTION 1
            mySale.date = listDate[3];
            mySale.volume = listVolume[3];

            Car.Add(mySale);


            //OPTION 2
            for (int i = 0; i < listDate.Count(); i++)
            {
                mySale.date = listDate[i];
                mySale.volume = listVolume[i];

                Car.Add(mySale);
            }

                foreach (int p in listVolume)
                Console.WriteLine(p);
                Console.WriteLine("\n"+Car[0].volume);

                Console.ReadLine();
    }

    }

    class mySales
    {
        public DateTime date { get; set; }
        public int volume { get; set; }
    }
}

1 Answer 1

2

mySales is a class, which is a reference type. In option 2, you are doing the following:

  1. You create mySale, which now is a reference to a specific instance of mySales.
  2. In the for loop, you modify mySale (which is still a reference to that exact same instance), and then add this same instance to the end of the list.

So at the end, when you've added mySale multiple times, you have a list with multiple references to the same instance.

What you probably want to do is define and instantiate mySale inside of the for loop, not outside.

Sign up to request clarification or add additional context in comments.

2 Comments

Awsome! It works very well when mySale is declared inside the loop. Thanks very much for the detailed explanation too.
@Guil75 That's what I'm here for :). If you liked my answer, would you consider marking it as correct?

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.