У нашому коді є дубль, який нам потрібно перетворити на int.
double score = 8.6;
int i1 = Convert.ToInt32(score);
int i2 = (int)score;
Хтось може мені пояснити, чому i1 != i2
?
Результат, який я отримую, такий: i1 = 9
і i2 = 8
.
У нашому коді є дубль, який нам потрібно перетворити на int.
double score = 8.6;
int i1 = Convert.ToInt32(score);
int i2 = (int)score;
Хтось може мені пояснити, чому i1 != i2
?
Результат, який я отримую, такий: i1 = 9
і i2 = 8
.
Відповіді:
Тому що Convert.ToInt32
тури:
Повернене значення: округляється до найближчого 32-бітного цілого числа, підписаного. Якщо значення знаходиться на півдорозі між двома цілими числами, повертається парне число; тобто 4,5 перетворюється на 4, а 5,5 перетворюється на 6.
... в той час як литий стриг :
Коли ви перетворюєте з подвійного або плаваючого значення в цілісний тип, це значення врізається.
Оновлення: див. Коментар Джеппе Стіга Нільсена нижче щодо додаткових розбіжностей (які, однак, не вступають у дію, якщо score
це справжнє число, як у випадку).
score
були 8.5
замість 8.6
. Я оновив відповідь, щоб включити цитати. Дякуємо за вклад.
score
це NaN
або нескінченність або скінченність, але виходить за межі діапазону Int32
, тоді Convert.ToInt32
викине виняток. Cast поверне int
, але ви не знаєте, який саме (на мою реалізацію це Int32.MinValue
), тому що ви знаходитесь в unchecked
контексті. (Якщо ви знаходитесь в checked
контексті, акторський склад буде винятком і у цих випадках.)
Double
тип типу 10000000000.6
(десять мільярдів балів шість) є "реальним" числом. Використання ролі int
на це дасть дивний результат (якщо ви не в checked
контексті, але ви, мабуть, не так).
Кастинг ігнорує що-небудь після десяткової крапки, тому 8,6 стає 8.
Convert.ToInt32(8.6)
це безпечний спосіб забезпечити округлення вашого подвійного до найближчого цілого числа, в цьому випадку 9.
У наведеному прикладі ваш десятковий знак - 8,6 . Якби це було 8,5 або 9,5, твердження i1 == i2, можливо, було б істинним. Інфакт був би правдою для 8,5, а помилковим - для 9,5.
Пояснення:
Незалежно від десяткової частини, другий вислів int i2 = (int)score
відкине десяткову частину і просто поверне вам цілу частину. Досить небезпечно робити, оскільки може статися втрата даних.
Тепер для першого твердження можуть статися дві речі. Якщо десяткова частина дорівнює 5, тобто вона знаходиться на півдорозі, слід прийняти рішення. Ми обходимо вгору чи вниз? У C # клас конвертувати реалізує заокруглення банкіра. Дивіться цю відповідь для більш глибокого пояснення. Простіше кажучи, якщо число парне, округніть вниз, якщо число непарне, округляйте вгору.
Наприклад, врахуйте:
double score = 8.5;
int i1 = Convert.ToInt32(score); // 8
int i2 = (int)score; // 8
score += 1;
i1 = Convert.ToInt32(score); // 10
i2 = (int)score; // 9
ToInt32 турів. Кастинг до int просто викидає не цілий компонент.
Math.Truncate(score)
є більш чітко вираженим наміром, ніж(int)score