1

I have a Form with two Datalog class variables

public partial class ModifyDataForm : Form
{
    public DataLog DLog;
    private DataLog copyCurrent;

    public ModifyDataForm(DataLog log, int selectIndex = 0)
    {
        InitializeComponent();
        DLog = (DataLog)log.Clone();
        copyCurrent = (DataLog)log.Clone();
    }
}

When I'm updating the value of DLog, the value of copyCurrent also changes, why?

The function in which I update the the variable is below

    private void smooth_Click(object sender, EventArgs e)
    {
        int NValues; int POrder;
        if (getSmoothParameters(out NValues, out POrder))//parameters are valid
        {
            float[] yvalues = DataLog.convertStringArrayToFloats(DLog.Data[labelIndex]);
            float[] newyvalues = Filters.smooth.SavitzkyGolay(yvalues, NValues, POrder);



            //I am updating the values of DLog here,
            //but the values of copyCurrent also changes
            DLog.Data[labelIndex] = Array.ConvertAll(newyvalues, x => AuxillaryFunctions.DecimalPlaceNoRounding((double)x));



            ((ViewDigiFiles)this.Owner).updateSelectedLog(DLog);
            ((ViewDigiFiles)this.Owner).glControl1.Invalidate();
        }
        else//parameters are NOT valid
        {
            MessageBox.Show("Invalid smoothing parameters.");
            return;
        }
    }
Chris
  • 681
  • 1
  • 6
  • 16

1 Answers1

6

The value of copyCurrent doesn't change. The data within the object that copyCurrent refers to may change, but that's a different matter.

Suppose you give two separate people (Alice and Bob) pieces of paper with your home address written on it. Alice goes and paints your front door red. Has that changed Bob's piece of paper? No - but if Bob visits the address on his piece of paper, he's still see a red front door.

This is a fundamental part of how value types and reference types work in C#. When a variable is of a reference type, its value isn't the object itself - it's a reference, which is like a street address - it's a way of navigating to an object. Copying the value of one variable into another just copies the reference, just like copying a street address from one piece of paper onto another.

It's very important to distinguish between variables, references, and objects. See my article on value types and reference types (or any good introductory C# book) for more details.

Jon Skeet
  • 1,421,763
  • 867
  • 9,128
  • 9,194
  • Thanks for the answer Jon, In this case would I have to write a copy constructor for the Datalog class in order to make copyCurrent a new independent object? – Chris Jul 29 '14 at 17:38
  • @Chris: Probably - we don't know anything about `Datalog`, so it's hard to tell what you should do. But it's vitally important that you understand the behaviour of reference types. – Jon Skeet Jul 29 '14 at 17:44
  • Problem solved! I copied the object by making the class serializable, and using the `ObjectCopier` class from [this post](http://stackoverflow.com/questions/78536/deep-cloning-objects/78551#78551) – Chris Jul 29 '14 at 18:33
  • @Chris: That sounds like a very heavy-weight way of copying an object. We don't really know what it is though, so it's hard to give alternatives. – Jon Skeet Jul 29 '14 at 18:47