Pertanyaan promosi floating-point: stroustrup vs compiler - siapa yang benar?


Pada bagian 10.5.1 dari buku baru Stroustrup "Bahasa Pemrograman C ++ - Edisi Keempat" katanya, bahwa sebelum operasi aritmatika dilakukan, promosi integral digunakan untuk membuat int dari tipe integer yang lebih pendek, dan juga, promosi floating-point adalah digunakan untuk membuat ganda dari pelampung.

Saya mengonfirmasi klaim pertama dengan kode berikut:

#include <iostream>
#include <typeinfo>

int main()
{
    short a;
    short b;
    std::cout << typeid(a + b).name() << std::endl;
}

Ini menghasilkan "int" dengan vc ++ dan "i" dengan gcc.

Tapi mengujinya dengan pelampung bukan celana pendek, hasilnya masih "mengambang" atau "f":

#include <iostream>
#include <typeinfo>

int main()
{
    float a;
    float b;
    std::cout << typeid(a + b).name() << std::endl;
}

Menurut Stroustrup tidak ada pengecualian untuk aturan promosi floating-point, jadi saya mengharapkan "dobel" atau "d" sebagai output.

Apakah bagian yang disebutkan tentang promosi salah atau tidak jelas? Dan apakah ada perbedaan dalam C ++ 98 dan C ++ 11 mengenai jenis promosi?


32
2018-06-20 13:53


asal


Jawaban:


Saya tidak tahu apa persisnya yang dikatakan buku Stroustrup, tetapi menurut standar, floats tidak akan dikonversi menjadi doubledalam hal ini. Sebelum menerapkan sebagian besar operator biner aritmatika, yang konversi aritmatika biasa dijelaskan dalam 5p9 diterapkan:

  • Jika salah satu operand adalah tipe enumerasi scoped (7.2), tidak ada konversi yang dilakukan; jika operan yang lain tidak memiliki tipe yang sama, ekspresi tersebut tidak terbentuk.
  • Jika operand adalah tipe double panjang, yang lain harus dikonversi ke double panjang.
  • Jika tidak, jika operan keduanya ganda, yang lain harus dikonversi menjadi dua kali lipat.
  • Jika tidak, jika operan baik mengambang, yang lain harus dikonversi menjadi mengambang.
  • Jika tidak, promosi integral (4.5) harus dilakukan pada kedua operan. [...]

Promosi integral inilah yang menyebabkan dua shorts untuk dikonversi menjadi ints. Tapi dua floats tidak akan dikonversi menjadi doublesesuai dengan aturan ini. Jika Anda menambahkan float ke a double, yang float akan dikonversi menjadi double.

Di atas adalah dari C ++ 11. C ++ 03 berisi aturan yang sama, kecuali yang mengacu pada enumerasi yang dibatasi.


29
2018-06-20 14:02



Sementara itu Stroustrup tampaknya mengakui kalimat referensi tidak benar atau setidaknya menyesatkan. Dia telah menghapus kalimat, tentang promosi titik apung, dari bagian 10.5.1.

Silahkan lihat errata pencetakan ke-3 edisi ke-4 pada halaman web Stroustrup:

pg 267: s / Demikian pula, promosi floating-point digunakan untuk membuat double out dari floats //

(Catatan: Ekspresi s / regexp / replacement / mirip dengan sed semantik alat unix. Ini mencari pola regexp dan menggantikannya dengan penggantian. Tidak ada dalam kasus kami.)


5
2017-09-20 18:57