Kok bisa di cuplikan berikut
int a = 7;
int b = 3;
double c = 0;
c = a / b;
c
akhirnya memiliki nilai 2, bukan 2,3333, seperti yang diharapkan. Jika a
dan b
adalah dobel, jawabannya berubah menjadi 2.333. Tapi tentunya karena c
sudah ganda seharusnya bekerja dengan bilangan bulat?
Jadi kenapa int/int=double
tidak berhasil?
c++
variables
double
integer-division
Jahoe
sumber
sumber
Jawaban:
Ini karena Anda menggunakan versi pembagian integer
operator/
, yang membutuhkan waktu 2int
detik dan mengembalikan sebuahint
. Untuk menggunakandouble
versi, yang mengembalikan adouble
, setidaknya salah satu dariint
s harus secara eksplisit dicor ke adouble
.sumber
a
danb
untukdouble
hanya untuk kejelasan, tapi itu benar-benar tidak peduli.static_cast<>
selalu tampak panjang lebar bagiku. Dalam kasus primitif, sebenarnya tidak ada bahaya tercampurstatic_cast<>
danreinterpret_cast<>
bercampur.static_cast
dalam kasus ini dan menggunakan cor gaya-C sebagai gantinya. Tidak ada manfaat dalam menggunakan cast gaya C ++ di sini dan mereka lebih mengacaukan kode daripada cast gaya C. Gips aritmatika adalah konteks yang tepat di mana gips gaya-C sangat tepat dan sebenarnya lebih sesuai daripada gips lainnya.double(b)
. Mereka tidak selalu menyadari bahwa ini adalah konversi, karena terlihat sama dengan panggilan konstruktor eksplisit.Ini dia:
a) Membagi dua
int
s selalu melakukan pembagian bilangan bulat. Jadi hasil daria/b
kasus Anda hanya dapat berupaint
.Jika Anda ingin mempertahankan
a
danb
sebagaiint
s, namun membaginya sepenuhnya, Anda harus membuang setidaknya satu untuk menggandakan:(double)a/b
ataua/(double)b
atau(double)a/(double)b
.b)
c
adalahdouble
, sehingga dapat menerima sebuahint
nilai pada assignement: yangint
secara otomatis dikonversi kedouble
dan ditugaskan untukc
.c) Ingatlah bahwa pada penugasan, ekspresi di sebelah kanan
=
dihitung pertama (menurut aturan (a) di atas, dan tanpa memperhatikan variabel di sebelah kiri=
) dan kemudian ditetapkan ke variabel di sebelah kiri=
(menurut ( b) di atas). Saya yakin ini melengkapi gambarannya.sumber
Dengan sedikit pengecualian (saya hanya dapat memikirkan satu), C ++ menentukan seluruh arti dari ekspresi (atau sub-ekspresi) dari ekspresi itu sendiri. Apa yang Anda lakukan dengan hasil ekspresi tidak menjadi masalah. Dalam kasus Anda, dalam ekspresi
a / b
, tidak ada yangdouble
terlihat; semuanyaint
. Jadi kompilator menggunakan pembagian integer. Hanya setelah hasilnya, barulah ia mempertimbangkan apa yang harus dilakukan dengannya, dan mengubahnya menjadidouble
.sumber
&funcname
bergantung pada jenis yang Anda gunakan.c
adalahdouble
variabel, tetapi nilai yang diberikan padanya adalahint
nilai karena dihasilkan dari pembagian duaint
s, yang menghasilkan "pembagian bilangan bulat" (menghilangkan sisanya). Jadi yang terjadi di garisc=a/b
adalaha/b
dievaluasi, membuat jenis sementaraint
c
setelah konversi ke jenisdouble
.Nilai
a/b
ditentukan tanpa mengacu pada konteksnya (penugasan kedouble
).sumber
Saat Anda membagi dua bilangan bulat, hasilnya akan menjadi bilangan bulat, terlepas dari fakta bahwa Anda menyimpannya dalam bentuk ganda.
sumber
Dalam bahasa C ++, hasil subekspresi tidak pernah terpengaruh oleh konteks sekitarnya (dengan beberapa pengecualian yang jarang terjadi). Ini adalah salah satu prinsip yang diikuti oleh bahasa dengan cermat. Ekspresi
c = a / b
berisi subekspresi independena / b
, yang ditafsirkan secara independen dari apa pun di luar subekspresi tersebut. Bahasa tidak peduli bahwa Anda nanti akan menetapkan hasilnya kedouble
.a / b
adalah divisi integer. Ada lagi yang tidak penting. Anda akan melihat prinsip ini diikuti di banyak sudut spesifikasi bahasa. Itulah cara kerja C ++ (dan C).Salah satu contoh pengecualian yang saya sebutkan di atas adalah penugasan / inisialisasi penunjuk fungsi dalam situasi dengan kelebihan beban
Ini adalah satu konteks di mana sisi kiri penugasan / inisialisasi memengaruhi perilaku sisi kanan. (Juga, inisialisasi referensi-ke-larik mencegah kerusakan jenis larik, yang merupakan contoh lain dari perilaku serupa.) Dalam semua kasus lain, sisi kanan mengabaikan sisi kiri sepenuhnya.
sumber
The
/
operator dapat digunakan untuk pembagian integer atau divisi floating point. Anda memberinya dua operan integer, sehingga melakukan pembagian integer dan hasilnya disimpan dalam double.sumber
Ini secara teknis bergantung pada bahasa, tetapi hampir semua bahasa memperlakukan subjek ini dengan sama. Jika ada jenis ketidakcocokan antara dua tipe data dalam ekspresi, sebagian besar bahasa akan mencoba mentransmisikan data di satu sisi
=
untuk mencocokkan data di sisi lain sesuai dengan sekumpulan aturan yang telah ditentukan.Saat membagi dua bilangan dengan tipe yang sama (integer, double, dll.), Hasilnya akan selalu sama (jadi 'int / int' akan selalu menghasilkan int).
Dalam hal ini Anda memiliki
double var = integer result
yang melemparkan hasil integer menjadi ganda setelah perhitungan dalam hal ini data pecahan sudah hilang. (kebanyakan bahasa akan melakukan pengecoran ini untuk mencegah ketidakakuratan jenis tanpa menimbulkan pengecualian atau kesalahan).Jika Anda ingin mempertahankan hasil ganda, Anda akan ingin menciptakan situasi yang Anda miliki
double var = double result
Cara termudah untuk melakukannya adalah dengan memaksa ekspresi di sisi kanan persamaan menjadi dua kali lipat:
c = a/(double)b
Pembagian antara integer dan double akan menghasilkan transmisi integer ke double (perhatikan bahwa ketika melakukan matematika, compiler akan sering "upcast" ke tipe data yang paling spesifik untuk mencegah kehilangan data).
Setelah upcast,
a
akan berakhir sebagai double dan sekarang Anda memiliki pembagian antara dua double. Ini akan membuat divisi dan tugas yang diinginkan.LAGI, harap dicatat bahwa ini khusus bahasa (dan bahkan dapat menjadi spesifik kompiler), namun hampir semua bahasa (tentu saja semua yang dapat saya pikirkan di luar kepala saya) memperlakukan contoh ini secara identik.
sumber
Yang penting salah satu elemen perhitungannya adalah tipe float-double. Kemudian untuk mendapatkan hasil ganda, Anda perlu memasukkan elemen ini seperti yang ditunjukkan di bawah ini:
atau c = a / static_cast (b);
Atau Anda dapat membuatnya secara langsung ::
Perhatikan bahwa salah satu elemen kalkulasi harus memiliki '.0' untuk menunjukkan pembagian tipe float-double dengan integer. Jika tidak, meskipun variabel c adalah double, hasilnya juga akan nol.
sumber