Heute bin ich beim Schreiben von Visual C ++ - Code auf etwas gestoßen, das mich überrascht hat. Es scheint, dass C ++ ++ (Inkrement) für Bool unterstützt, aber nicht - (Dekrement). Ist dies nur eine zufällige Entscheidung, oder gibt es einen Grund dafür?
Dies kompiliert:
static HMODULE hMod = NULL;
static bool once = false;
if (!once++)
hMod = LoadLibrary("xxx");
Das tut nicht:
static HMODULE hMod = NULL;
static bool once = true;
if (once--)
hMod = LoadLibrary("xxx");
++once
undonce++
arbeite mit gcc, aber nicht mit den Dekrementen.bool
veraltet ist .std::exchange(once,false)
(Hinweis: nicht atomar) ersetzt werden, wenn Sie etwas nicht veraltetes möchten.Antworten:
Es stammt aus der Geschichte der Verwendung von Ganzzahlwerten als Boolesche Werte.
Wenn dies ein
x
istint
, aber ich es als Booleschenif(x)...
Wert gemäß gemäß Inkrementierung verwende, bedeutet dies, dass unabhängig von seinem Wahrheitswert vor der Operation ein Wahrheitswert vontrue
danach vorliegt (außer bei Überlauf).Es ist jedoch unmöglich, das Ergebnis des
--
gegebenen Wissens nur über den Wahrheitswert von vorherzusagenx
, da dies zufalse
(wenn der Integralwert 1 ist) odertrue
(wenn der Integralwert etwas anderes ist - insbesondere zu 0 [false
] und 2 oder mehr [true
]).Also als Short-Hand
++
gearbeitet und--
nicht.++
ist auf Bools aus Kompatibilitätsgründen zulässig, seine Verwendung ist jedoch im Standard veraltet.Dies setzt voraus , dass ich nur verwenden
x
als boolean, dass Überlauf bedeutet , kann nicht passieren , bis ich getan habe++
oft genug , um einen Überlauf zu verursachen , auf seine eigene ist. Selbst mit char als verwendetem Typ undCHAR_BITS
etwas Niedrigem wie 5 ist das 32 Mal, bevor dies nicht mehr funktioniert (das ist immer noch ein Argument genug, um eine schlechte Praxis zu sein, ich verteidige die Praxis nicht, sondern erkläre nur, warum sie funktioniert). Für ein 32-Bitint
müssten wir natürlich++
2 ^ 32 mal verwenden, bevor dies ein Problem ist. Mit--
obwohl wird es nur ergeben,false
wenn ich mit einem Wert von 1 fürtrue
oder mit 0 angefangen und++
genau einmal zuvor verwendet habe.Dies ist anders, wenn wir mit einem Wert beginnen, der nur wenige unter 0 liegt. In einem solchen Fall möchten wir möglicherweise
++
denfalse
Wert schließlich wie folgt erhalten :Doch dieses Beispiel behandelt
x
alsint
überall mit Ausnahme der Bedingung, so ist es gleichbedeutend mit:Was sich von der Verwendung nur
x
als Boolescher Wert unterscheidet.quelle
<limits.h>
Header und dasCHAR_BIT
Makro erfunden . Zuvor hätte es theoretisch Implementierungen geben können, diechar
schmaler als 8 Bit sind, aber meines Wissens gab es keine. Insbesondere listet K & R1 (veröffentlicht 1978) 4 Beispielimplementierungen auf, die alle 8-Bit oder 9-Bit habenchar
.CHAR_BIT >= 8
. Der Standard berücksichtigt keine Ziele, bei denen dies schwierig ist. (Sie könnten natürlich eine nicht konforme Implementierung haben.)ANSI ISO IEC 14882 2003 (c ++ 03):
5.2.6-2
Und nicht überraschend ...
5.3.2-2
Auch in 5.6.2-1 und 5.3.2-1 wird erwähnt, dass ++ für Bools wahr sein soll, und Anhang D-1 besagt, dass ++ für Bools veraltet ist.
quelle
Aus historischen Gründen wurde dies unterstützt. Beachten Sie jedoch Folgendes: Die Verwendung eines Operanden vom Typ bool mit dem Operator ++ ist veraltet, siehe Abschnitt 5.3.2 im C ++ - Standard (n3092).
5.3.2 Inkrementieren und Dekrementieren [expr.pre.incr]
quelle
quelle