Konvertieren Sie ein uint32_t in ein int32_t, ohne dass das Risiko eines Überlaufs oder einer übermäßigen Komplexität besteht

8

Wie kann ich ein uint32_t schnell in ein int32_t mit dem Wrapping in C ++ konvertieren?

Einige Versuche:

%Vor%     
Demi 18.04.2016, 21:16
quelle

3 Antworten

5

int32_t x = (int32_t)y; ist kein Überlauf und nicht UB. Überlauf ist, wenn eine arithmetische Operation ein Ergebnis außerhalb des Bereichs der darstellbaren Werte erzeugt. Eine Konvertierung ist jedoch keine arithmetische Operation.

Diese Situation ist implementierungsdefiniertes Verhalten. Alle Implementierungen, von denen ich weiß, definieren das Verhalten so, dass sie die Repräsentation nicht verändern.

Beachten Sie, dass hier kein Cast erforderlich ist. Sie können int32_t x = y; schreiben. In der Praxis ist dies einfacher und wird immer funktionieren. So viel Code verlässt sich darauf, dass kein Anbieter jemals ein anderes Verhalten definieren wird (nicht, dass sie irgendeinen Grund dafür haben).

int32_t x = *(int32_t*)&y ist nicht UB. Es verletzt kein striktes Aliasing, da die signierte Version eines Typs die unsignierte Version als Alias ​​verwenden darf. Dieser Code erzeugt garantiert die int32_t mit der gleichen Repräsentation wie die entsprechende uint32_t (d. H. "Wrapping", da diese Typen garantiert das Zweierkomplement sind).

    
M.M 18.04.2016, 22:13
quelle
5
%Vor%

Dies und memcpy(&uint_var, &int_var, sizeof uint_var) sind die beiden Standardmethoden, um eine solche Konvertierung durchzuführen, ohne undefiniertes Verhalten aufzurufen.

Siehe auch:

a3f 18.04.2016 21:25
quelle
1
%Vor%     
Roland Illig 18.04.2016 21:29
quelle

Tags und Links