Ich bin ein C ++ - Anfänger und lese Bjarne Stroustrups Programmierung: Prinzipien und Praxis mit C ++ .
Im Abschnitt 3.9.2 Unsichere Konvertierungen erwähnte der Autor
Wenn der Initialisierer ein ganzzahliges Literal ist, kann der Compiler den tatsächlichen Wert überprüfen und Werte akzeptieren, die keine Verengung implizieren:
int char b1 {1000}; // error: narrowing (assuming 8-bit chars)
Diese Erklärung verwirrt mich. Es werden zwei Typen ( int
und char
) verwendet. Ich habe noch nie eine solche Erklärung in Java und Swift gesehen (die beiden Sprachen, mit denen ich relativ vertraut bin). Ist das ein Tippfehler oder eine gültige C ++ - Syntax?
float char
ist ein weiterer nützlicher Typ, insbesondere in Schwimmbädern. Einige kommen mit einem Halter für ein Bier.Antworten:
Es ist ein Fehler im Buch. Dies ist keine gültige C ++ - Deklaration, auch ohne die vermeintlich einschränkende Konvertierung.
Es wird jedoch in keiner der Erratas auf der Seite von Bjarne Stroustrup (4. Druck und früher) erwähnt, was seltsam ist. Es ist ein klarer Fehler. Ich stelle mir vor, da es mit
//error
wenigen Leuten kommentiert wird , die den Fehler in der Erklärung selbst bemerken.quelle
char b1 {1000};
(weil dies den im Kommentar erwähnten Fehler provozieren würde). Ich denke, Bjarnes Tippfinger waren an diesem Tag müde.int
! :-)Das Buch ist falsch.
Die Token-Sequenz
int char b1{1000};
ist in C ++ nicht semantisch gültig.Sie versuchen,
b1
mit mehr als einem Typ zu deklarieren , was keinen Sinn ergibt.quelle
Es ist falsch. In C / C ++ können die Deklarationen mit mehreren Typen über die Verwendung von Gewerkschaften erreicht werden. Z.B:
union { int i; char c; } var; var.i = 42; /* OR */ var.c = ‘c’;
Der Speicher ist derselbe, daher sind .c und .i nur Typ-Handles mit demselben Wert.
quelle
Dies ist in der C / C ++ - Syntax falsch. Zusätzlich zu
union
s (siehe @ Alex-Antwort) gibt es eine C ++ - Möglichkeit, nur einen der verfügbaren Typen mit dem Namenstd::variant
(type-safe union) zu speichern :#include <variant> #include <string> int main() { std::variant<int, float> v, w; v = 12; // v contains int int i = std::get<int>(v); w = std::get<int>(v); w = std::get<0>(v); // same effect as the previous line w = v; // same effect as the previous line // std::get<double>(v); // error: no double in [int, float] // std::get<3>(v); // error: valid index values are 0 and 1 try { std::get<float>(w); // w contains int, not float: will throw } catch (std::bad_variant_access&) {} std::variant<std::string> v("abc"); // converting constructors work when unambiguous v = "def"; // converting assignment also works when unambiguous }
quelle