C # 'da double'ı int türüne dönüştürme


108

Kodumuzda int'e dönüştürmemiz gereken bir çiftimiz var.

double score = 8.6;
int i1 = Convert.ToInt32(score);
int i2 = (int)score;

Biri bana nedenini açıklayabilir i1 != i2mi?

Aldığım sonuç şudur: i1 = 9ve i2 = 8.


5
Math.Truncate(score)niyeti daha açık bir şekilde ifade eder(int)score
Lu55

4
Ancak
Math.Truncate

Yanıtlar:


172

Çünkü Convert.ToInt32mermi:

Dönüş Değeri: en yakın 32 bitlik işaretli tam sayıya yuvarlanır. Değer iki tam sayının ortasındaysa, çift sayı döndürülür; yani 4.5, 4'e ve 5.5, 6'ya dönüştürülür.

... alçı kesilirken :

Double veya float değerden integral türe dönüştürdüğünüzde, değer kesilir.

Güncelleme: Ek farklılıklar için aşağıdaki Jeppe Stig Nielsen'in yorumuna bakın (ancak scoreburada olduğu gibi gerçek bir sayı ise oyuna girmez ).


6
Bağlantınız aslında bunu en iyi şekilde açıklar ve yuvarlak vs kesik kadar basit değildir: Type: System.Int32 değeri, en yakın 32 bitlik işaretli tam sayıya yuvarlanır. Değer iki tam sayının ortasındaysa, çift sayı döndürülür; yani, 4.5 4'e ve 5.5 6'ya dönüştürülür.
ericosg

@ericosg: Evet, eğer bu farkı maske olacağını scoreidi 8.5yerine 8.6. Cevabı alıntıları içerecek şekilde güncelledim. Giriş için teşekkürler.
Jon

6
Ve eğer scoreolduğunu NaNya bir sonsuzluk ya sonlu ama dışarıda aralığı Int32, daha sonra Convert.ToInt32bir özel durum oluşturur. Oyuncular bir döndürür int, ancak hangisinin olduğunu (benim uygulamamda olduğunu Int32.MinValue) bilemezsiniz çünkü uncheckedbağlam içindesiniz . ( checkedBağlam içinde olursanız , bu durumlarda oyuncu kadrosu da bir istisna oluşturacaktır.)
Jeppe Stig Nielsen

@JeppeStigNielsen: Giriş için teşekkürler, bunu da belirtmek için cevabı güncelledim.
Jon

Güzel. Ama bence Doubletip numarası 10000000000.6(on milyar nokta altı) "gerçek" bir sayıdır. Bunun intüzerine bir cast kullanmak garip bir sonuç verecektir ( checkedbağlam içinde değilseniz , ancak muhtemelen değilsiniz).
Jeppe Stig Nielsen

15

Kullanmak, ondalık noktadan sonraki her şeyi yok sayar, dolayısıyla 8.6, 8 olur.

Convert.ToInt32(8.6) çiftinizin en yakın tam sayıya yuvarlanmasını sağlamanın güvenli yoludur, bu durumda 9.


1
Bonus soru - değeri eğer ne olur ikizi haline itmek için çok büyük int ? Yani int.MAX_VAL'den yüksekse ?
Konrad Viltersten

1
@KonradViltersten bir istisna atıyor Değer bir Int32 için çok büyük ya da çok küçüktü.
Vamsi

11

dublörünüzü yuvarlayabilir ve ist:

(int)Math.Round(myDouble);

4
soru şimdi nasıl yapılacağıydı i1 == i2. Soru neden eşit olmadıklarıyla ilgiliydi . Olumsuz oy verildi.
Adam

6

Verilen örnekte ondalık değeriniz 8.6'dır . 8.5 veya 9.5 olsaydı, i1 == i2 ifadesi doğru olabilirdi. Aslında, 8.5 için doğru ve 9.5 için yanlış olurdu.

Açıklama:

Ondalık kısım ne olursa olsun, ikinci ifade int i2 = (int)scoreondalık kısmı atacak ve size tamsayı kısmını döndürecektir. Veri kaybı olabileceği için yapılması oldukça tehlikeli bir şey.

Şimdi, ilk ifade için iki şey olabilir. Ondalık kısım 5 ise, yani yarı yolda ise, bir karar verilmelidir. Yukarı mı yoksa aşağı mı yuvarlıyoruz? C # 'de, Convert sınıfı bankerin yuvarlamasını uygular. Daha derin açıklama için bu yanıta bakın . Basitçe söylemek gerekirse, sayı çift ise aşağı yuvarlayın, tek sayı ise yukarı yuvarlayın.

Örneğin şunları düşünün:

        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

2

ToInt32 mermi. İnt'e çevrim, tamsayı olmayan bileşeni atar.

Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.