enum - Größe garantieren
-
Hi,
also ich programmiere gerade ein programm das sich übers netzwerk verbindet und dieses soll natürlich auf 64 bit sowie 32 bit laufen.
nur habe ich in meinem packet das ich versende einen mit enum definierten datentyp, und mein compiler sagt mir das standartmäßig die enum typen als int ( 32 bit ) behandelt werden und ich möchte jetzt aber garantiert haben das das 4 byte variabeln sind ohne meinen coding style verwerfen zu müssen. ( sprich enum durch eine einfache __int32 ersetzen )
-
enum ist standard-mäßig ein int...
ob es auf 64bit systemen auch 32bit groß ist, kann ich dir leider nicht genau sagen, aber das geht eigtl ganz einfach zu umgehen:- falls du unter windows programmierst und nur mit msvc compilieren willst, dann kannste das so machen: (neues feature, was von gcc imho noch nicht unterstützt wird (weil der standard noch nicht verabschiedet ist ^^) - der msvc kann das aber schon
)enum xyz : int { //einträge wie gewohnt }- falls eine bestimmte _mindest_ - größe reicht:
enum xyz { //einträge wie gehabt _forceINT = 0xffffffff; //4 bytes }bevor du jz mit c++ kommst und statt
0xffffffffeinen wert aus numeric_limits nehmen möchtest: würde ich von abraten, weil dann das ergebnis wieder compiler-abhängig ist...bb
-
Ganz nebenbei, es ist auch nicht garantiert, daß int 32 Bit groß ist. Wenn du Daten in einem plattformunabhängigen Format über's Netz schicken möchtest, solltest du für die Datenpakete immer feste Größen verwenden, die nicht von den Datentypen des jeweiligen Compilers abhängen. Das gilt für enum genauso wie für int, von daher würde auch die Größe von enums dem Compiler überlassen, und für's Senden der Daten dann beispielsweise auf int32 o.ä. casten.
-
dooooomi schrieb:
Ganz nebenbei, es ist auch nicht garantiert, daß int 32 Bit groß ist.
deshalb meine einschränkung mit nur msvc... weil da ein int eben doch 32bit lang ist - immer ^^
und ich find es ein wenig dumm jedes mal wieder dieses _theoretische_ problem auszudiskutieren... ich kann mir jedenfalls nicht vorstellen, dass man freiwillig nen compiler nimmt, bei dem nem int nicht genau 32 bit sind...dooooomi schrieb:
für's Senden der Daten dann beispielsweise auf int32 o.ä. casten
Jopp - das ist die unabhängiger Lösung ^^ aber es war gefragt, wie er das enum sicher auf eine bestimmte größe bekommt, deshalb meine antwort mit dem _forceint bzw. vererbung oder wie man das bei enums nennt... ^^
bb
-
Wenn man das Feature mit dem Doppelpunkt und dem Typen danach nur unter MSVC nutzen kann, kann man gleich davon ausgehen, dass
intbei dieser IDE 32 Bit gross ist.unskilled, welchen Effekt hat das
_forceINTgenau? Würde das nicht auch abgeschnitten, fallsenum-Typen weniger als 4 Byte hätten?
-
Nexus schrieb:
unskilled, welchen Effekt hat das
_forceINTgenau? Würde das nicht auch abgeschnitten, fallsenum-Typen weniger als 4 Byte hätten?ne - es sorgt dafür, dass das enum mind. 4 Byte bekommt...
wird auch sehr oft in den direct 3d headern gemacht (da hab ich es damals zumindest das erste mal gesehen)logischerweise kann ein compiler so nen enum:
enum a { a1, a2 }als char/short oder als int (oder größer?) behandeln - damit das char und short wegfällt gibt es eben diesen trick:
enum a { a1, a2, _forceINT = 0xffffffff }aber größer als nen int kann das enum dadurch trotzdem noch werden - ich weiß nicht, ob enum nen größt-möglichen typen besitzt deshalb kann ich nicht sicher sagen, dass es dann lt. standard genau 4byte ist...
bb
-
unskilled schrieb:
und ich find es ein wenig dumm jedes mal wieder dieses _theoretische_ problem auszudiskutieren... ich kann mir jedenfalls nicht vorstellen, dass man freiwillig nen compiler nimmt, bei dem nem int nicht genau 32 bit sind...
Naja, ganz so theoretisch ist das Problem auch wieder nicht. Natürlich ist ein int auf x86-64 unter allen gängigen Betriebssystemen nur 32 Bit groß. Es gibt aber andere 64-Bit Plattformen (jenseits von x86), auf denen int tatsächlich 64 Bit groß ist (was ja irgendwo auch logisch ist). Und ja, auch solche Plattformen benutzt man freiwillig

-
Hm, das wusste ich bisher nicht. Der Standard sagt dazu Folgendes:
7.2/5 schrieb:
The underlying type of an enumeration is an integral type that can represent all the enumerator values defined in the enumeration. It is implementation-defined which integral type is used as the underlying type for an enumeration except that the underlying type shall not be larger than int unless the value of an enumerator cannot fit in an int or unsigned int.
Also darf der
enum-Typ nicht grösser alsintsein, wenn alle Werte mitintdargestellt werden können.
-
gut - also ist der weg mit _forceint = 0xffffffff doch der beste weg ^^
bb
-
danke für die vielen antworten,
ich benutze jetzt enum : typ {... da ich eine genaue größere forcieren muss und nicht eine minmalgröße garantieren
aber auch vielen dank für diese möglichkeit ^^
-
Warum benutzt du dann nicht einfach uint32 oder int32 anstatt des enums. int ist beim gcc auf 64bit Maschinen auch 64bit lang.
-
knivil schrieb:
int ist beim gcc auf 64bit Maschinen auch 64bit lang.
Jein. Wie weiter oben schon erwähnt gibt es durchaus Plattformen, wo dem so ist. Auf einem normalen x86-64 Linux, OS X oder Windows ist int aber nach wie vor nur 32 Bit groß. Man sollte sich nur nicht drauf verlassen, wenn man wirklich plattformunabhängigen Code schreiben will.
-
knivil schrieb:
Warum benutzt du dann nicht einfach uint32 oder int32 anstatt des enums.
Wieso anstatt?
enum-Typen sind mit anderen integralen Typen nicht gleichzusetzen.
-
Schurke schrieb:
ich benutze jetzt enum : typ
dann nimm (wie gesagt) int32 als typ...
Aber da Nexus oben geschrieben hat, dass lt Standard ein enum nicht größer sein darf, als ein int (ich geh einfach mal davon aus, dass du keine 2^32 einträge in das enum packen willst - und ich denke auch mal, dass das die wenigsten compiler unterstützen werden... ^^), dann kannst du auch die lösung mit dem _forceInt = 0xffffffff nehmen...
bb