2011-01-12 9 views
1

Obwohl es viele Zeilen zum Thema reinterpret_cast gab, und wie schlecht es ist, bin ich immer noch verwirrt mit dem besten Weg, es zu vermeiden, besonders im Umgang mit Funktionen wie Lese und schreibe von fstream. Also, hier ist mein Dilemma ...Richtiges Casting für fstream Lesen und Schreiben von Elementfunktionen

Nehmen wir an, wir haben ein Integer-Array, das wir mit einigen Daten aus einer Datei füllen wollen.

std::ifstream iFile(...); 

// presume that the type of this array is not a matter of choice 
int *a = new int[ 100 ]; 

Wir waren mit ein paar verschiedenen Abgüssen lesen:

iFile.read((char *)a, sizeof(int) * 100); 
iFile.read(reinterpret_cast< char * >(a), sizeof(int) * 100); 
iFile.read(static_cast< char * >(static_cast< void * >((a)), sizeof(int) * 100); 

Die erste (C-Stil) ist veraltet und neue Casts wir in C++ eingeführt aus guten Gründen. Der zweite ist unportabel und bietet keine Garantien. Der dritte ist langweilig zu schreiben und den Spaß zu verdirzen.

Gibt es eine Alternative dazu und wie soll ich darüber gehen?

EDIT:

Das Ziel ist, Code als portable zu erreichen und als normgerechte wie möglich.

+2

Der dritte ist verzögert. Ich verstehe nicht, warum du keine reinterpret_cast verwenden kannst. Aber was genau meinen Sie mit "unportabel und bietet keine Garantien"? Beziehen Sie sich auf Endianness und mögliche zukünftige Änderungen der Größe von int? –

+1

Obwohl das Verhalten von 'reininterpret_cast' technisch nicht garantiert ist, ist dieser Fall genau das, wofür Sie es verwenden sollten. Die meisten Implementationen unterscheiden sich kaum zwischen einem C-Style-Cast und einem "Reinterpret_cast". –

+1

Das Verhalten von reinterpret_cast ist möglicherweise nicht definiert. Aber die Spezifikation sagt auch * es soll nicht überraschend für diejenigen sein, die die Adressierungsstruktur der zugrunde liegenden Maschine kennen * Also angenommen, Sie kennen Ihre Maschine (ein Standard-PC) sollte es gut funktionieren. –

Antwort

3

Warum gehst du nicht erklären a als char* stattdessen wie folgt aus:

//int *a = new int[100]; 
char *a = new char[100]; 
iFile.read(a, 100); 

Kein Casting jetzt erforderlich.


EDIT:

Okay, ich lese Ihre Kommentare und die Kommentarzeile in Ihrem Beitrag. In diesem Fall:

iFile.read(reinterpret_cast<char*>(a), sizeof(int)*100); 

sollte ausreichen.

Allerdings würde ich persönlich C-Casts wählen:

iFile.read((char*)a, sizeof(int)*100); 

Das ist, weil ich hier keine Gefahr nicht sehen. Alles scheint gut zu sein, sogar mit C-Style-Besetzung!


Beste noch weniger langweilig Guss

diese Funktion Vorlage definieren:

template<class To, class From> 
To any_cast(From v) 
{ 
    return static_cast<To>(static_cast<void*>(v)); 
} 

dann verwenden:

//`From` type will be inferred from the function argument. :-) 
iFile.read(any_cast<char*>(a), sizeof(int)*100); 

Sieht gut aus?

Ich denke, das any_cast kann verwendet werden, um von Any-Typ zu Any-Typ zu werfen!

+0

Sagen wir einfach, ich habe dort keine Option. Der Kommentar über dieser Zeile muss Sie übersprungen haben. – LavaScornedOven

+0

Sie können ein int * nicht an ein char * übergeben. –

+0

@PigBen: oops .. ich meinte 'reinterpret_cast' ... korrigierte es! – Nawaz