I have a string variable and a string constant. Both should be the same value (I'm testing for equality in a conditional). The 'correct' values of both should be "scl". While debugging, if I put a watch on each, look at them in the 'locals' windows, or hover over them, the value displayed is "sd", which is the value of a different constant in the class (there are many other constants and variables in the class that are displaying values correctly). If I insert a Debug.WriteLine for the variable/constant value in question, (in the same scope as the watch) the output window prints the correct value of each. For the life of me, I can't figure out why this is happening, or how to correct it.
A:
Is it a lazy loaded property? I've had issues like this in the past where I've done something like this (horribly contrived example, but it will do)
public ClassWithMoo
{
private string moo;
public string Moo
{
get
{
if (String.IsNullOrEmpty(this.moo)) this.moo = "Baa";
return this.moo;
}
set
{
this.moo = value;
}
}
}
public ClassThatUsesMoo
{
ClassWithMoo cow = new ClassWithMoo();
// breakpoint here would show cow.Moo = "Baa"
// This is because the debugger/watch window will instantiate the property!
someCodeHere();
cow.Moo = "Moo";
debug.WriteLine(cow.Moo); // outputs 'Moo' now that it has been set properly
}
PaulG
2010-06-28 19:05:35
That would make sense. However, nothing like that is being done. Besides, one of the erroneous values is of a constant, so reassigning the constant to the proper value could not be done.
Matthew Ives
2010-06-28 19:16:14
+1
A:
I seemed to have fixed it by changing the value of the constant, running a debugging session, then changing the value back to what it should be. Perhaps this cleared out some kind of debugging cache.
Thanks for the help all!
Matthew Ives
2010-06-28 19:38:06
I think I know what happened. The semantics of a constant are supposed to be that the value is *constant* for *all eternity*. The compiler assumes that a constant *never* changes, even between versions of an assembly. Therefore, when assembly B references a constant C from assembly A, the compiler *embeds* the value of C in B. If you then change the constant in A, B still has the original value, and will until you recompile B. If you want the value to be something that is picked up at runtime, use a property or readonly field instead.
Eric Lippert
2010-06-28 20:50:20