Hallo bitte verzeiht meine Frage, aber ich bim mit C noch ganz am Anfang. In meinem C-Buch ist nur von unsigned bzw. signed char die Rede, aber hier im Forum schreibt man dafür "uint_8" usw. Woher kennt der Compiler uint_8 ? Btw. gibt es auch uint_64 oder gar uint_128 ?
Maddel ihm sein Kumpel schrieb: > Woher kennt der Compiler uint_8 ? Überhaupt nicht. Er kennt ggf. uint8_t. Siehe stdint.h
Maddel ihm sein Kumpel schrieb: > Hallo bitte verzeiht meine Frage, aber ich bim mit C noch ganz am > Anfang. In meinem C-Buch ist nur von unsigned bzw. signed char die > Rede, Evtl. ist dein Buch dann etwas veraltet. Die typedefs aus stdint.h sind seit 1999 offizieller Bestandteil von C.
Maddel ihm sein Kumpel schrieb: > In meinem C-Buch ist nur von unsigned bzw. signed char die > Rede, aber hier im Forum schreibt man dafür "uint_8" usw. uint8_t ist ein unsigned integer Type mit exakt 8 Bit Breite. char ist ein Datentyp (implementationsabhängig signed oder unsigned) mit mindestens 8 Bit Breite, aber groß genug um ein Zeichen des systemspezifischen Character-Sets aufzunehmen. Ich habe zwar noch keinen Compiler gesehen, wo dass so ist, theoretisch könnten das aber auch mehr als 8 Bit sein. Da die meisten Compiler auf einem 8-Bit Character-Sets basieren ist uint8_t in der Regel nur ein Alias auf unsigned char, definiert in <stdint.h>. Das muss aber nicht so sein. (Das alls sagt zumindest mein C++ Standard. Ich unterstelle mal, dass das in C genauso ist.)
A. H. schrieb: > Da die meisten Compiler auf einem 8-Bit Character-Sets > basieren ist uint8_t in der Regel nur ein Alias auf unsigned char, > definiert in <stdint.h>. Das muss aber nicht so sein. Naja, viele andere Möglichkeiten gibt es nicht, denn kleiner als char kann uint8_t nicht sein, und größer kann er auch nicht sein.
Es gibt/gab ein paar DSPs (bspw. TMS320Cxx und MC56000), die keine 8-Bit-Bytes adressieren können. Bei denen hat dann ein char die Wortbreite des Prozessors (bspw. 24 oder 32 Bit). Ein uint8_t gibt es auf solchen Prozessoren nicht.
Rolf Magnus schrieb: > denn kleiner als char > kann uint8_t nicht sein, und größer kann er auch nicht sein. Warum glaubst du das?
Stefan Rand schrieb: > Rolf Magnus schrieb: >> denn kleiner als char kann uint8_t nicht sein, und größer kann er auch >> nicht sein. > > Warum glaubst du das? Ich weiß es, weil die logische Konsequenz aus den Regeln von ISO C ist. char ist der kleinstmögliche Typ (sizeof(char) ist per Definition 1). Also kann uint8_t nicht kleiner sein. Und größer als char kann uint8_t natürlich auch nicht sein, denn char ist ja mindestens 8 Bit groß, also so groß wie uint8_t.
Stefan Rand schrieb: >> denn kleiner als char kann uint8_t nicht sein > > Warum glaubst du das? Weil man bei uint8_t < char in arge Bedrängnis gerät. Da char auch für ein sogenanntes Byte und die kleinste adressierbare Einheit steht, zumindest aus Sicht von C, wäre ein uint8_t kleiner als char nicht mehr adressierbar. Es wäre aber als bizarres Zugeständnis an jene Programmierer denkbar, die bei 9 Bit Bytes trotzdem jenseits 255 einen Überlauf erwarten. uint8_t würde dann 8 Bits im 9 Bit Byte speichern, mit künstlichem Überlauf wie bei 8 Bit Daten.
:
Bearbeitet durch User
> Ich weiß es, weil die logische Konsequenz aus den Regeln von ISO C > ist. char ist der kleinstmögliche Typ (sizeof(char) ist per Definition > 1). Also kann uint8_t nicht kleiner sein. > Und größer als char kann uint8_t natürlich auch nicht sein, denn char > ist ja mindestens 8 Bit groß, also so groß wie uint8_t. http://www.unix.com/man-page/posix/7posix/stdint.h/:
1 | Note: The "width" of an integer type is the number of bits used to store its value in a |
2 | pure binary system; the actual type may use more bits than that (for example, a |
3 | 28-bit type could be stored in 32 bits of actual storage). An N-bit signed type has |
4 | values in the range -2**N-1 or 1-2**N-1 to 2**N-1-1, while an N-bit unsigned type |
5 | has values in the range 0 to 2**N-1. |
Es geht hier um die Anzahl der Bits, die verwendet werden, um den Wertebereich eines Typs darzustellen, nicht um die Anzahl der Bits, die verwendet werden, um einen Wert dieses Typs zu speichern.
A. K. schrieb: > Es wäre aber als bizarres Zugeständnis an jene Programmierer denkbar, > die bei 9 Bit Bytes trotzdem jenseits 255 einen Überlauf erwarten. > uint8_t würde dann 8 Bits im 9 Bit Byte speichern, mit künstlichem > Überlauf wie bei 8 Bit Daten. Genau das sagt meiner Ansicht nach der Standard aus. Für uint8_t – wenn er denn existiert – sollte gelten 0xff+0x01 == 0x00. Für char ist das nicht garantiert.
Rolf Magnus schrieb: > Stefan Rand schrieb: >> Rolf Magnus schrieb: >>> denn kleiner als char kann uint8_t nicht sein, und größer kann er auch >>> nicht sein. >> >> Warum glaubst du das? > > Ich weiß es, weil die logische Konsequenz aus den Regeln von ISO C > ist. char ist der kleinstmögliche Typ (sizeof(char) ist per Definition > 1). Also kann uint8_t nicht kleiner sein. > Und größer als char kann uint8_t natürlich auch nicht sein, denn char > ist ja mindestens 8 Bit groß, also so groß wie uint8_t. Naja, nur wenn uint8_t existiert, aber klar, da habe ich mich blöd ausgedrückt. Ich meinte den Fall, daß char größer acht Bit ist, womit uint8_t schlecht ein typedef auf unsigned char sein kann. Aber das ist halt eine Aussage über eine nicht existierende Entität, und insofern wirklich unspannend.
A. H. schrieb: > Es geht hier um die Anzahl der Bits, die verwendet werden, um den > Wertebereich eines Typs darzustellen, nicht um die Anzahl der Bits, die > verwendet werden, um einen Wert dieses Typs zu speichern. Das würde aber immer noch bedeuten, daß uin8t_t zwar nicht alle Bits nutzen, aber trotzdem mindestens so viele wie char haben muß. Das ist allerdings POSIX und nicht ISO C. In C99 steht die von dir zitierte "Note" nicht. Was mich jetzt, nachdem ich mal in C99 mal ein bischen nachgelesen habe, wundert, ist die Unterscheidung zwischen signed und unsigned (Das gleiche steht auch in deiner verlinkten Man-Page). Bei signed heißt es da: ****************************** The typedef name intN_t designates a signed integer type with width N , no padding bits, and a two’s complement representation. Thus, int8_t denotes a signed integer type with a width of exactly 8 bits. ****************************** "No padding bits" heißt, daß alle Bits genutzt werden müssen. Bei unsigned fehlt dieser Teil jedoch: ****************************** The typedef name uintN_t designates an unsigned integer type with width N. Thus, uint24_t denotes an unsigned integer type with a width of exactly 24 bits. ****************************** Das würde ja heißen, daß uint8_t auch 12 Bit groß sein und dann nur 8 bits benutzen dürfte, int8_t dagegen alle 12 Bits nutzen müßte. Ich bin verwirrt...
Ok, kurz nach dem Posten noch den Logikfehler entdeckt. int8_t dürfte ja nicht 12 Bits nutzen, sondern eben nur 8. Das würde dann aber bedeuten, daß es im Speicher auch immer exakt 8 Bit belegen muß, wodurch dann in der Konsequenz das gleiche für uint8_t gelten würde.
Rolf Magnus schrieb: > In C99 steht die von dir zitierte "Note" nicht. Kann sie auch nicht. POSIX ist nur mit Zweierkomplementdarstellung verträglich. C ist demgegenüber neutral, erlaubt z.B. auch das Einerkomplement.
:
Bearbeitet durch User
Rolf Magnus schrieb: > "No padding bits" heißt, daß alle Bits genutzt werden müssen. Bei > unsigned fehlt dieser Teil jedoch: In C11 nicht mehr.
A. K. schrieb: > Rolf Magnus schrieb: >> In C99 steht die von dir zitierte "Note" nicht. > > Kann sie auch nicht. POSIX ist nur mit Zweierkomplementdarstellung > verträglich. C ist demgegenüber neutral, erlaubt z.B. auch das > Einerkomplement. Das Zitat von oben ist aus C99, wo für intN_t explizit eine > two’s complement representation gefordert ist. Hat sich das in C11 auch geändert? Ich hab leider nur C99 zur Verfügung. A. K. schrieb: > Rolf Magnus schrieb: >> "No padding bits" heißt, daß alle Bits genutzt werden müssen. Bei >> unsigned fehlt dieser Teil jedoch: > > In C11 nicht mehr. Ok, dann war es, wie ich mir schon dachte, nur ein Fehler in C99.
Rolf Magnus schrieb: > Evtl. ist dein Buch dann etwas veraltet. Die typedefs aus stdint.h sind > seit 1999 offizieller Bestandteil von C. Oh ja ist von 1989. Also soll man anstelle von z.B. signed long long int besser int64_t schreiben. Ist ja kürzer und schneller zu schreiben. Oder gibt es sonst noch Vor oder Nachteile?!
Maddel ihm sein Kumpel schrieb: > Also soll man anstelle von z.B. > signed long long int besser int64_t schreiben. > Ist ja kürzer und schneller zu schreiben. > Oder gibt es sonst noch Vor oder Nachteile?! int64_t ist ein Typ, der exakt 64 Bit breit ist. Den solltest du dann verwenden, wenn du an der Stelle darauf angewiesen bist, daß es wirklich genau 64 Bit sind.
Rolf Magnus schrieb: > gefordert ist. Hat sich das in C11 auch geändert? Ich hab leider nur C99 > zur Verfügung. Ich lag oben falsch, POSIX drückt sich letztlich nur anders aus. Die Sprache an sich ist neutral, bestimmte Definitionen bezüglich der Umgebung, wie die zu uintN_t, sind es aber auch im Standard nicht. C11 draft n1570: http://www.compsci.hunter.cuny.edu/~sweiss/resources/c11standard.pdf
:
Bearbeitet durch User
Bitte melde dich an um einen Beitrag zu schreiben. Anmeldung ist kostenlos und dauert nur eine Minute.
Bestehender Account
Schon ein Account bei Google/GoogleMail? Keine Anmeldung erforderlich!
Mit Google-Account einloggen
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.