Ich möchte a verwenden Track-Bar
, um Form
die Deckkraft von a zu ändern .
Das ist mein Code:
decimal trans = trackBar1.Value / 5000;
this.Opacity = trans;
Wenn ich die Anwendung erstelle, wird der folgende Fehler angezeigt:
Konvertieren kann nicht implizit Art
decimal
zudouble
Ich habe versucht, trans
und double
dann Control
funktioniert das nicht. Dieser Code hat in einem früheren VB.NET-Projekt einwandfrei funktioniert.
c#
floating-point
type-conversion
double
decimal
Eier McLaren
quelle
quelle
Antworten:
Eine explizite Besetzung, um
double
dies zu mögen, ist nicht erforderlich:Es ist ausreichend, die Konstante als
5000.0
(oder als5000d
) zu identifizieren :quelle
Eine allgemeinere Antwort auf die generische Frage "Decimal vs Double?": Dezimal für monetäre Berechnungen, um die Genauigkeit zu erhalten, Double für wissenschaftliche Berechnungen, die nicht von kleinen Unterschieden betroffen sind. Da Double ein Typ ist, der in der CPU nativ ist (interne Darstellung wird in Basis 2 gespeichert ), sind mit Double durchgeführte Berechnungen besser als Decimal ( intern in Basis 10 dargestellt ).
quelle
Ihr Code hat in VB.NET einwandfrei funktioniert, da er implizit alle Casts ausführt, während C # sowohl implizite als auch explizite Casts enthält.
In C # ist die Konvertierung von dezimal nach doppelt explizit, da Sie an Genauigkeit verlieren. Zum Beispiel kann 1.1 nicht genau als Doppel ausgedrückt werden, sondern als Dezimalzahl (siehe " Gleitkommazahlen - ungenauer als Sie denken " aus dem Grund dafür).
In VB wurde die Konvertierung vom Compiler für Sie hinzugefügt:
Dies
(double)
muss explizit in C # angegeben werden, kann aber vom VB-Compiler "verzeihender" impliziert werden.quelle
Warum dividierst du durch 5000? Stellen Sie einfach die Minimal- und Maximalwerte der TrackBar zwischen 0 und 100 ein und teilen Sie den Wert durch 100 für den Deckkraftprozentsatz. Das folgende Beispiel mit mindestens 20 verhindert, dass das Formular vollständig unsichtbar wird:
quelle
5000
, hätte OP ein Problem mit100
?Sie haben zwei Probleme. Erstens
Opacity
erfordert ein Doppel, kein Dezimalwert. Der Compiler teilt Ihnen mit, dass es zwar eine Konvertierung zwischen Dezimal und Doppel gibt, es sich jedoch um eine explizite Konvertierung handelt, die Sie angeben müssen, damit sie funktioniert. Der zweite ist, dassTrackBar.Value
es sich um einen ganzzahligen Wert handelt und das Teilen eines int durch ein int zu einem int führt, unabhängig davon, welcher Art von Variable Sie es zuweisen. In diesem Fall gibt es eine implizite Umwandlung von int in dezimal oder doppelt - da bei der Umwandlung kein Genauigkeitsverlust auftritt - der Compiler beschwert sich also nicht, aber der Wert, den Sie erhalten, ist vermutlich immer 0, datrackBar.Value
ist immer kleiner als 5000. Die Lösung besteht darin, Ihren Code so zu ändern, dass double (der native Typ für Deckkraft) und Gleitkomma-Arithmetik verwendet wird, indem die Konstante explizit zu einem Double gemacht wird - was die Arithmetik fördert - odertrackBar.Value
zu Double umgewandelt wird , die das Gleiche tun - oder beides. Oh, und Sie brauchen die Zwischenvariable nur, wenn sie anderweitig verwendet wird. Ich vermute, der Compiler würde es sowieso weg optimieren.quelle
Meiner Meinung nach ist es wünschenswert, so explizit wie möglich zu sein. Dies erhöht die Klarheit des Codes und hilft Ihren Programmierkollegen, die ihn möglicherweise lesen.
Zusätzlich zum (oder anstelle von) Anhängen von a
.0
an die Nummer können Sie verwendendecimal.ToDouble()
.Hier sind einige Beispiele:
quelle
Es hört sich so an, als wäre
this.Opacity
es ein doppelter Wert, und der Compiler mag es nicht, wenn Sie versuchen, einen Dezimalwert hinein zu stopfen.quelle
Die Opacity- Eigenschaft ist vom doppelten Typ:
oder einfach:
oder:
Beachten Sie, dass ich
5000.0
(oder5000d
) verwende, um eine doppelte Division zu erzwingen, datrackBar1.Value
es sich um eine Ganzzahl handelt und eine Ganzzahldivision durchgeführt wird und das Ergebnis eine Ganzzahl ist.quelle
Sie sollten
5000.0
anstelle von verwenden5000
.quelle
Angenommen, Sie verwenden WinForms,
Form.Opacity
ist vom Typdouble
, daher sollten Sie Folgendes verwenden:Sofern Sie den Wert nicht an anderer Stelle benötigen, ist es einfacher zu schreiben:
Der Grund, warum das Steuerelement nicht funktioniert, wenn Sie Ihren Code so geändert haben, dass er einfach doppelt ist, war, dass Sie:
was das
5000
als eine ganze Zahl interpretierte , und weiltrackbar1.Value
es auch eine ganze Zahl ist, war Ihrtrans
Wert immer Null. Indem.0
der Compiler die Zahl explizit zu einem Gleitkommawert macht, indem er den numerischen Wert hinzufügt, kann er sie jetzt als Doppel interpretieren und die richtige Berechnung durchführen.quelle
Die beste Lösung ist:
quelle
Da
Opacity
es sich um einen Doppelwert handelt, würde ich von Anfang an nur ein Doppel verwenden und überhaupt nicht wirken. Achten Sie jedoch darauf, beim Teilen ein Doppel zu verwenden, damit Sie keine Präzision verlierenquelle
quelle