Namespaces
Variants

Increment/decrement operators

From cppreference.net
C++ language
General topics
Flow control
Conditional execution statements
Iteration statements (loops)
Jump statements
Functions
Function declaration
Lambda function expression
inline specifier
Dynamic exception specifications ( until C++17* )
noexcept specifier (C++11)
Exceptions
Namespaces
Types
Specifiers
constexpr (C++11)
consteval (C++20)
constinit (C++20)
Storage duration specifiers
Initialization
Expressions
Alternative representations
Literals
Boolean - Integer - Floating-point
Character - String - nullptr (C++11)
User-defined (C++11)
Utilities
Attributes (C++11)
Types
typedef declaration
Type alias declaration (C++11)
Casts
Memory allocation
Classes
Class-specific function properties
Special member functions
Templates
Miscellaneous

Inkrement-/Dekrement-Operatoren erhöhen oder verringern den Wert des Objekts.

Operatorname Syntax Überladbar Prototypbeispiele (für class T )
Innerhalb der Klassendefinition Außerhalb der Klassendefinition
Prä-Inkrement ++a Ja T & T :: operator ++ ( ) ; T & operator ++ ( T & a ) ;
Prä-Dekrement --a Ja T & T :: operator -- ( ) ; T & operator -- ( T & a ) ;
Post-Inkrement a++ Ja T T :: operator ++ ( int ) ; T operator ++ ( T & a, int ) ;
Post-Dekrement a-- Ja T T :: operator -- ( int ) ; T operator -- ( T & a, int ) ;
Hinweise
  • Die Präfix-Versionen der eingebauten Operatoren geben Referenzen zurück und die Postfix-Versionen geben Werte zurück. Typische benutzerdefinierte Überladungen folgen diesem Muster, damit die benutzerdefinierten Operatoren auf die gleiche Weise wie die eingebauten verwendet werden können. Allerdings kann bei einer benutzerdefinierten Operatorüberladung jeder Typ als Rückgabetyp verwendet werden (einschließlich void ).
  • Der int -Parameter ist ein Dummy-Parameter, der zur Unterscheidung zwischen Präfix- und Postfix-Versionen der Operatoren dient. Wenn der benutzerdefinierte Postfix-Operator aufgerufen wird, ist der in diesem Parameter übergebene Wert immer null, obwohl er durch Aufruf des Operators mittels Funktionsaufrufnotation geändert werden kann (z.B. a. operator ++ ( 2 ) oder operator ++ ( a, 2 ) ).

Inhaltsverzeichnis

Präfixoperatoren

Die Präfix-Inkrement- und Dekrement-Ausdrücke haben die Form

++ Ausdruck
-- Ausdruck
1) Präfix-Inkrement (Pre-Increment)
2) Präfix-Dekrement (Pre-Decrement)

Eingebaute Präfixoperatoren

1) Der Ausdruck ++ x ist äquivalent zu x + = 1 , mit folgenden Ausnahmen:
  • Wenn der Typ von expression (möglicherweise volatile-qualifiziert) bool ist, wird expression auf true gesetzt. Eine solche Inkrementierung ist veraltet.
(bis C++17)
  • Wenn der Typ von expression (möglicherweise cv-qualifiziert) bool ist, ist das Programm fehlerhaft.
(seit C++17)
  • Wenn der Typ von expression volatile-qualifiziert ist, ist die Inkrementierung veraltet.
(seit C++20)
2) Der Ausdruck -- x ist äquivalent zu x - = 1 , mit folgenden Ausnahmen:
  • Wenn der Typ des Ausdrucks (möglicherweise cv-qualifiziert) bool ist, ist das Programm fehlerhaft.
  • Wenn der Typ des Ausdrucks volatile-qualifiziert ist, ist das Dekrement veraltet.
(seit C++20)

Überladungen

Bei Überlagerungsauflösung gegenüber benutzerdefinierten Operatoren nehmen für jeden optional flüchtig-qualifizierten arithmetischen Typ A außer bool und für jeden optional flüchtig-qualifizierten Zeiger P auf optional cv-qualifizierte Objekttypen die folgenden Funktionssignaturen an der Überlagerungsauflösung teil:

A & operator ++ ( A & )
bool & operator ++ ( bool & )
(veraltet) (bis C++17)
P & operator ++ ( P & )
A & operator -- ( A & )
P & operator -- ( P & )

Postfix-Operatoren

Die Postfix-Inkrement- und Dekrement-Ausdrücke haben die Form

Ausdruck ++
Ausdruck --
1) Postfix-Inkrement (Post-Inkrement)
2) Postfix-Dekrement (Post-Dekrement)

Eingebaute Postfix-Operatoren

Das Ergebnis des Postfix-Inkrements oder -Dekrements ist der Wert, der durch Anwendung der Lvalue-zu-Rvalue-Konvertierung auf expression (vor der Modifikation) erhalten wird. Der Typ des Ergebnisses ist die cv-unqualifizierte Version des Typs von expression .

Wenn expression kein modifizierbarer L-Wert eines arithmetischen Typs außer (möglicherweise cv-qualifiziertem) bool (seit C++17) oder ein Zeiger auf einen vollständigen Objekttyp ist, ist das Programm fehlerhaft.

Wenn der Typ von expression volatile-qualifiziert ist, ist das Inkrement oder Dekrement als veraltet markiert.

(since C++20)
1) Der Wert des Ausdrucks wird so modifiziert, als wäre er der Operand des Präfix- ++ Operators.
2) Der Wert des Ausdrucks wird so geändert, als ob er der Operand des Präfix- -- Operators wäre.

Die Wertberechnung einer Postfix-Inkrement- oder -Dekrement-Operation ist sequenced before der Modifikation des expression . In Bezug auf einen indeterminately-sequenced Funktionsaufruf ist die Operation eines Postfix-Inkrements oder -Dekrements eine single evaluation.

Überladungen

Bei Überlagerungsauflösung gegenüber benutzerdefinierten Operatoren nehmen für jeden optional flüchtig qualifizierten arithmetischen Typ A außer bool und für jeden optional flüchtig qualifizierten Zeiger P auf einen optional cv-qualifizierten Objekttyp die folgenden Funktionssignaturen an der Überlagerungsauflösung teil:

A operator ++ ( A & , int )
bool operator ++ ( bool & , int )
(veraltet) (bis C++17)
P operator ++ ( P & , int )
A operator -- ( A & , int )
P operator -- ( P & , int )

Beispiel

#include <iostream>
int main()
{
    int n1 = 1;
    int n2 = ++n1;
    int n3 = ++ ++n1;
    int n4 = n1++;
//  int n5 = n1++ ++;   // Fehler
//  int n6 = n1 + ++n1; // undefiniertes Verhalten
    std::cout << "n1 = " << n1 << '\n'
              << "n2 = " << n2 << '\n'
              << "n3 = " << n3 << '\n'
              << "n4 = " << n4 << '\n';
}

Ausgabe:

n1 = 5
n2 = 2
n3 = 4
n4 = 4

Hinweise

Aufgrund der beteiligten Nebeneffekte müssen die eingebauten Inkrement- und Dekrementoperatoren mit Vorsicht verwendet werden, um undefiniertes Verhalten aufgrund von Verstößen gegen die Sequenzierungsregeln zu vermeiden.

Da während des Post-Inkrements und Post-Dekrements eine temporäre Kopie des Objekts erstellt wird, sind Prä-Inkrement- oder Prä-Dekrement-Operatoren in Kontexten, in denen der zurückgegebene Wert nicht verwendet wird, in der Regel effizienter.

Standardbibliothek

Inkrement- und Dekrementoperatoren sind für viele Standardbibliothekstypen überladen. Insbesondere überlädt jeder LegacyIterator den operator ++ und jeder LegacyBidirectionalIterator überlädt den operator -- , selbst wenn diese Operatoren für den spezifischen Iterator No-Ops sind.

Überladungen für arithmetische Typen
erhöht oder verringert den atomaren Wert um eins
(öffentliche Elementfunktion von std::atomic<T> )
erhöht oder verringert die Tickanzahl
(öffentliche Elementfunktion von std::chrono::duration<Rep,Period> )
Überladungen für Iteratortypen
bewegt den Iterator vorwärts
(öffentliche Elementfunktion von std::raw_storage_iterator<OutputIt,T> )
bewegt den reverse_iterator vorwärts oder rückwärts
(öffentliche Elementfunktion von std::reverse_iterator<Iter> )
bewegt den move_iterator vorwärts oder rückwärts
(öffentliche Elementfunktion von std::move_iterator<Iter> )
No-Op
(öffentliche Elementfunktion von std::front_insert_iterator<Container> )
No-Op
(öffentliche Elementfunktion von std::back_insert_iterator<Container> )
No-Op
(öffentliche Elementfunktion von std::insert_iterator<Container> )
bewegt den Iterator vorwärts
(öffentliche Elementfunktion von std::istream_iterator<T,CharT,Traits,Distance> )
No-Op
(öffentliche Elementfunktion von std::ostream_iterator<T,CharT,Traits> )
bewegt den Iterator vorwärts
(öffentliche Elementfunktion von std::istreambuf_iterator<CharT,Traits> )
No-Op
(öffentliche Elementfunktion von std::ostreambuf_iterator<CharT,Traits> )
bewegt den Iterator zur nächsten Übereinstimmung
(öffentliche Elementfunktion von std::regex_iterator<BidirIt,CharT,Traits> )
bewegt den Iterator zur nächsten Teilübereinstimmung
(öffentliche Elementfunktion von std::regex_token_iterator<BidirIt,CharT,Traits> )

Fehlerberichte

Die folgenden verhaltensändernden Fehlerberichte wurden rückwirkend auf zuvor veröffentlichte C++-Standards angewendet.

DR Angewendet auf Verhalten wie veröffentlicht Korrektes Verhalten
CWG 2855 C++98 übliche arithmetische Konvertierungen wurden für eingebaute Prä-Inkrement- und
Prä-Dekrement-Operatoren angewendet, aber nicht für ihre Postfix-Pendants [1]
ebenfalls angewendet
CWG 2901 C++98 Lvalue-zu-Rvalue-Konvertierungen wurden nicht angewendet
für eingebaute Post-Inkrement- und Post-Dekrement-Operatoren
angewendet
  1. Das Präfix ++ x ist äquivalent zu x + = 1 , und letzteres ist für übliche arithmetische Konvertierungen anwendbar (d.h. ergibt einen gemeinsamen Typ zwischen decltype ( x ) und int ). Allerdings ist die Wirkung des Postfix x ++ einfach "Eins zu x addieren", es ist kein binärer Operator vorhanden, daher finden keine üblichen arithmetischen Konvertierungen statt.

Siehe auch

Operator-Präzedenz

Operatorüberladung

Häufige Operatoren
Zuweisung Inkrement
Dekrement
Arithmetik Logisch Vergleich Member
Zugriff
Sonstige

a = b
a + = b
a - = b
a * = b
a / = b
a % = b
a & = b
a | = b
a ^ = b
a <<= b
a >>= b

++ a
-- a
a ++
a --

+ a
- a
a + b
a - b
a * b
a / b
a % b
~a
a & b
a | b
a ^ b
a << b
a >> b

! a
a && b
a || b

a == b
a ! = b
a < b
a > b
a <= b
a >= b
a <=> b

a [ ... ]
* a
& a
a - > b
a. b
a - > * b
a. * b

Funktionsaufruf

a ( ... )
Komma

a, b
Bedingungsoperator

a ? b : c
Spezielle Operatoren

static_cast konvertiert einen Typ in einen anderen verwandten Typ
dynamic_cast konvertiert innerhalb von Vererbungshierarchien
const_cast fügt cv -Qualifizierer hinzu oder entfernt sie
reinterpret_cast konvertiert Typ zu einem unverwandten Typ
C-style cast konvertiert einen Typ zu einem anderen durch eine Kombination von static_cast , const_cast und reinterpret_cast
new erstellt Objekte mit dynamischer Speicherdauer
delete zerstört zuvor durch den new-Ausdruck erstellte Objekte und gibt den bezogenen Speicherbereich frei
sizeof fragt die Größe eines Typs ab
sizeof... fragt die Größe eines Pack ab (seit C++11)
typeid fragt die Typinformationen eines Typs ab
noexcept prüft, ob ein Ausdruck eine Exception werfen kann (seit C++11)
alignof fragt die Ausrichtungsanforderungen eines Typs ab (seit C++11)

C-Dokumentation für Increment/decrement operators