Warum ist b [2] falsch?


11
string s;
bool b[] = {s=="",  s==s.c_str(),  s.c_str()==""};

setzt

b[] = {true, true, false};

Warum ist b[2]falsch?

Wenn A==Bund A==C, sollte das nicht bedeuten B==C?



Ich sehe jetzt meinen Fehler und habe ein Gefühl von Deja Vu, da es nicht das erste Mal ist, dass ich mich beim Vergleichen von Zeigern verwirrt habe.
NoComprende

Antworten:


14

In diesem Ausdruck

s.c_str()==""

Es werden zwei Zeiger (Adressen) verglichen. Der erste ist der von zurückgegebene Zeiger s.c_str()und der zweite ist der Zeiger auf das erste Zeichen (Abschlusszeichen Null) des Zeichenfolgenliteral "".

Es ist offensichtlich, dass die Adressen unterschiedlich sind (denken Sie auch daran, dass das Zeichenfolgenliteral die statische Speicherdauer hat).

Um das erwartete Ergebnis zu erhalten, sollten Sie stattdessen schreiben

std::strcmp( s.c_str(), "" ) == 0

Wie für diese beiden Ausdrücke

s==""

und

s==s.c_str()

Dann werden Zeichenfolgen verglichen, da die Standardklasse std :: string den Operator == für den richtigen Operanden überladen hat.


Garantiert der Standard im letzten Fall, dass die Zeiger unterschiedlich sind? Ich verstehe, dass sie sein können.
Jeffrey

Kann nur hinzufügen, dass es UB sein sollte. "Vergleich mit String-Literal führt zu nicht spezifiziertem Verhalten"
Roout

@Jeffrey Es garantiert, weil zumindest die Zeichenfolge leer ist. :) In jedem Fall verwendet die Klasse std :: string eine Kopie eines Arguments ihres Konstruktors.
Vlad aus Moskau

1
@Roout - "UB" bedeutet undefiniertes Verhalten ". Dies bedeutet, dass die Sprachdefinition nicht sagt, wie sich das Programm ** verhält . Ein Programm mit undefiniertem Verhalten ist kein gültiges C ++ - Programm." Nicht spezifiziertes Verhalten "bedeutet dies Es gibt mehrere Alternativen, und der Standard sagt Ihnen nicht, welche davon ausgewählt werden. Das Programm ist gültig, und die Implementierung kann eine der Alternativen auswählen.
Pete Becker

@PeteBecker Ein Programm mit UB ist immer noch ein gültiges C ++ - Programm (zumindest in dem Sinne, dass es erfolgreich kompiliert wurde und ausgeführt werden kann).
Trolley813
Durch die Nutzung unserer Website bestätigen Sie, dass Sie unsere Cookie-Richtlinie und Datenschutzrichtlinie gelesen und verstanden haben.
Licensed under cc by-sa 3.0 with attribution required.