To jest naprawdę dziwne. Byłem tropienia ten błąd:Odmienne zachowanie podczas odlewania
Negating the minimum value of a twos complement number is invalid.
... i okazało się, że to ze względu na kod tak:
var valueFromUser = "470259123000000";
var doubleValue = Convert.ToDouble(valueFromUser, CultureInfo.InvariantCulture);
Math.Abs((int)doubleValue);
Rzeczywiście, kiedy biegnę to w LINQPad:
(int)Convert.ToDouble("470259123000000", CultureInfo.InvariantCulture)
... to daje mi:
-2147483648
Jednakże, inny deweloper tutaj mówi, że robi się coś zupełnie innego (nie w LINQPad):
-1141206336
Kiedy próbuję oceniać tylko do obsady sam na Constant:
(int)470259123000000.0
... ja uzyskać błąd kompilacji z powodu konieczności unchecked
. I tak:
unchecked((int)470259123000000.0)
... ocenia się -1141206336
jak drugi deweloper dostaje. Pomyślałem więc, że może Convert
stworzył subtelnie inną wartość niż stała. Nie, to ocenia się True
:
Convert.ToDouble("470259123000000", CultureInfo.InvariantCulture) == 470259123000000.0
Co do cholery się tu dzieje? Dlaczego ocena tych pozornie identycznych wyrażeń daje tak różne wyniki?
Aktualizacja:
Znaleziony podpowiedź. Reprezentacja hex 4.70259123E14
i -1141206336
jest:
0x42FABB2BBFA92C00
0xBBFA92C0
Sądzę więc, że jednym z odlewów jest popychanie bity bezpośrednio do int
. Tak więc -2147483648
jest większą tajemnicą.
interesujące. Wydaje się, że istnieje różnica między sprawdzonymi i niezaznaczonymi zachowaniami rzutowania.Korzystając z zaawansowanej aplikacji "Kalkulator" (oczywiście w trybie "Programmer" ;-) Widzę, że '-1141206336' pasuje do obciętego (32 lsb)' 470259123000000'. Sprawdzona wersja wydaje się zwracać 'int.MinValue'. Jestem pewien, że ktoś będzie mógł wskazać to w specyfikacji językowej. – Alex