2012-08-14 12 views
8

Ich habe eine benutzerdefinierte WebControl, die implementiert eine .Value Getter/Setter eine Nullable <dezimal> RückkehrVerständnis der Null-Koaleszenz-Operator (??)

Es ist eine clientseitige gefilterten Textbox (eine Unterklasse von TextBox mit Javascript enthalten und einige serverseitige Logik zum Einstellen/getting den Wert)

ist die Getter & die Setter aus dieser Kontrolle:

public decimal? Value 
{ 
    get 
    { 
     decimal amount = 0; 
     if (!decimal.TryParse(this.Text, NumberStyles.Currency, null, out amount)) 
     { 
      return null; 
     } 
     else 
     { 
      return amount; 
     } 
    } 
    set 
    { 
     if (!value.HasValue) 
     { 
      this.Text = ""; 
     } 
     else 
     { 
      this.Text = string.Format("${0:#,##0.00}", value); 
     } 
    } 
} 

Das Problem, das ich sehe, ist, dass die Ausgabe von dieser Aussage:

decimal Amount = uxAmount.Value ?? 0M; 

I Betrag sehe eingestellt wird auf „0“, wenn uxAmount.Value kehrt 10000.

Das funktioniert, wie ich (Entschuldigung erwartet die Änderung Gehäuse):

decimal? _Amount = uxAmount.Value; 
decimal amount = _Amount ?? 0; 

ich auch dieses Verhalten (vor kurzem gesehen haben), wenn eine UDF-Funktion definiert auf einem Linq2Sql Datenkontext zusammen mit dem null-Koaleszenz-Operator ruft, also ich meine UDF Anruf wusste, dass die erwartete zurückgegeben Wert aber ich war ge Tting den RHS-Wert stattdessen.

Weitere verwirrend mich, wenn ich uxAmount.Value in der Uhr auswerte, bekomme ich 10000 vom Typ Nullable<decimal>.

Hier sind einige Ausdrücke, die ich versucht habe:

decimal? _Amount = uxAmount.Value; //10000 
decimal amount = _Amount ?? 0; //10000 
decimal amount2 = _Amount ?? 0M; //10000 
decimal Amount = uxAmount.Value ?? 0M; //0 

Dann habe ich diesen Ausdruck nach oben 4

decimal amount3 = (uxTaxAmount.Value) ?? 0M; 

Jetzt

decimal Amount = uxAmount.Value ?? 0M; //10000 
decimal amount3 = (uxAmount.Value) ?? 0M; //0 

Es scheint, wie das letzte Gespräch ist immer 0, aber der Wert uxAmount.Value (der ausgeparst wird 10 wie oben Getter/Setter mit einem TryParse ist stabil. Ich bin an einem Haltepunkt angehalten und es gibt keine anderen Threads, die diesen Wert manipulieren könnten.

Beachten Sie die Verwendung des M-Suffixes, um die Konstante zu dezimieren, da es ganzzahlig war und ich ein Typkonvertierungsproblem vermutete.

Irgendwelche Ideen?

Der Wert von sowohl LHS als auch RHS scheint stabil und bekannt zu sein.

--edit-- einige screen von VS2010

Stepping through the code showing the value of amount3

Watch dialog and some more detail about state of variables

+0

CurrencyTextBox (eine Unterklasse von TextBox) – agrath

+1

Es ist ein Nullwert-Dezimal [Dezimal?] - siehe die Getter/Setter-Definition am Anfang der Frage – agrath

+1

Sind Sie sicher, der Debugger dsiplays dies korrekt für Sie? Hast du versucht, ein paar Zeilen weiter runter zu gehen, um sicherzustellen, dass du den aktualisierten Wert von 'Menge3' hast? Weil, wenn 'XXX' eine nullwertfähige Dezimalzahl ist, dann' XXX ?? 0M' ist eine (nicht nullbare) Dezimalstelle, die den Wert von 'XXX' hat, wenn diese nicht null ist, andernfalls den Wert Null. –

Antwort

0

(Diese Antwort wurde von meinen Kommentaren oben konstruiert.)

Sind Sie sicher, dass der Debugger dsiplays dies für Sie richtig? Haben Sie versucht, einige Zeilen weiter nach unten zu stellen, um sicherzustellen, dass Sie den aktualisierten Wert amount3 haben?

Ich bin sicher, es ist nur ein Problem mit dem Debugger. Manchmal muss man etwas weiter gehen. Vielleicht hat der übersetzte Code (IL) einige Optimierungen, die den Debugger verwirren (oder was würde ich wissen). Aber ohne den Debugger wird der Wert genau dann aktualisiert, wenn Sie es erwarten.

Ich habe andere erfahrene Entwickler durch ähnliche Situationen verwirrt gesehen, daher weiß ich, dass der Debugger manchmal "eine Zeile Code" hinter sich hat, wenn er sich eine Zuweisung zu einer lokalen Variablen anschaut. Vielleicht kann jemand einen Link finden, der das diskutiert?

1

Werfen Sie einen Blick auf diese ähnliche Frage

using coalescing null operator on nullable types changes implicit type

warum nicht einfach tun

decimal amount = uxTaxAmount.Value.HasValue ? uxTaxAmount.Value.Value : 0M 

Dies ist nicht die richtige Antwort auf die Probleme mit Originalplakaten nach den letzten Änderungen und Kommentaren.

+0

Stellt sich heraus, es ist ein Debugger-Problem.Ich war sehr besorgt, dass meine Verwendung von ?? hatte eine Menge unbekannter Nebenwirkungen und ich musste über alle meine Projekte gehen und sicherstellen, dass ich die Syntax geändert habe – agrath

+0

Auch, .Wert ist dezimal? (Nullable ) – agrath

+0

oh hatte ich nicht, dass die Verbindung herstellen, da seine ein Nullable-dezimal der tatsächliche Wert Value.Value würde :) –