uint8_t est justement introduit dans la norme pour définir un entier non
signé 8 bits. Le "unsigned char" n'est pas forcément 8 bits.
Mouarf. Bon, oui, d'accord. Ce que je voulais dire, c'est que pour un
débutant, sizeof(char) == 1.
C'est comme sizeof(void*) != sizeof(void (*)(void)): oui, ça existe.
Mais pour un débutant, il vaut mieux l'oublier, cela ne sert à rien de
complexifier à l'extrème les choses.
uint8_t est justement introduit dans la norme pour définir un entier non
signé 8 bits. Le "unsigned char" n'est pas forcément 8 bits.
Mouarf. Bon, oui, d'accord. Ce que je voulais dire, c'est que pour un
débutant, sizeof(char) == 1.
C'est comme sizeof(void*) != sizeof(void (*)(void)): oui, ça existe.
Mais pour un débutant, il vaut mieux l'oublier, cela ne sert à rien de
complexifier à l'extrème les choses.
uint8_t est justement introduit dans la norme pour définir un entier non
signé 8 bits. Le "unsigned char" n'est pas forcément 8 bits.
Mouarf. Bon, oui, d'accord. Ce que je voulais dire, c'est que pour un
débutant, sizeof(char) == 1.
C'est comme sizeof(void*) != sizeof(void (*)(void)): oui, ça existe.
Mais pour un débutant, il vaut mieux l'oublier, cela ne sert à rien de
complexifier à l'extrème les choses.
Moi je t'avoue, j'en ai *marre* de corriger du code de debutant monte
en pousse qui me fout des void* dans des int
Plus tot le debutant prendra quelques bons reflexes, comme d'appeler un
chat un chat, mieux ca vaudra pour tout le monde.
Moi je t'avoue, j'en ai *marre* de corriger du code de debutant monte
en pousse qui me fout des void* dans des int
Plus tot le debutant prendra quelques bons reflexes, comme d'appeler un
chat un chat, mieux ca vaudra pour tout le monde.
Moi je t'avoue, j'en ai *marre* de corriger du code de debutant monte
en pousse qui me fout des void* dans des int
Plus tot le debutant prendra quelques bons reflexes, comme d'appeler un
chat un chat, mieux ca vaudra pour tout le monde.
D'un autre côté le surcharger avec des notions qu'il n'utilisera
probablement jamais (je veux dire, un informaticien de base ne touchera
jamais à autre chose qu'à des processeurs de pc ou de serveur) n'est
peut être pas utile pour l'instant
D'un autre côté le surcharger avec des notions qu'il n'utilisera
probablement jamais (je veux dire, un informaticien de base ne touchera
jamais à autre chose qu'à des processeurs de pc ou de serveur) n'est
peut être pas utile pour l'instant
D'un autre côté le surcharger avec des notions qu'il n'utilisera
probablement jamais (je veux dire, un informaticien de base ne touchera
jamais à autre chose qu'à des processeurs de pc ou de serveur) n'est
peut être pas utile pour l'instant
Merci Eric pour les précisions sur les char, byte et octet.
Moi, je défini mon buffer ainsi :
uint8_t buf[1024];
Est-ce donc correct, et
- si non, comment je dois le déclaré (car buf[1024]?) ?
- si oui, est-ce bien utile que j'utilise le masque 0xff (puisque
uint8_t est un octet) ?
Merci Eric pour les précisions sur les char, byte et octet.
Moi, je défini mon buffer ainsi :
uint8_t buf[1024];
Est-ce donc correct, et
- si non, comment je dois le déclaré (car buf[1024]?) ?
- si oui, est-ce bien utile que j'utilise le masque 0xff (puisque
uint8_t est un octet) ?
Merci Eric pour les précisions sur les char, byte et octet.
Moi, je défini mon buffer ainsi :
uint8_t buf[1024];
Est-ce donc correct, et
- si non, comment je dois le déclaré (car buf[1024]?) ?
- si oui, est-ce bien utile que j'utilise le masque 0xff (puisque
uint8_t est un octet) ?
Moi je t'avoue, j'en ai *marre* de corriger du code de debutant monte
en pousse qui me fout des void* dans des int
Je reformule: dan la vraie vie, on a souvent sizeof(void*) != sizeof(int), et
il est en effet important de le signaler (de même que sizeof(long) n'est pas
forcément >= sizeof(void*))
Dans le cas du sizeof((signed|unsigned) char), c'est tellement rare que dans
la pratique les quelques cas spécifiques (à la DSP, par exemple) seront de
toute manière tellement bien cadrés que cela ne posera pa de problèmes.Plus tot le debutant prendra quelques bons reflexes, comme d'appeler un
chat un chat, mieux ca vaudra pour tout le monde.
D'un autre côté le surcharger avec des notions qu'il n'utilisera probablement
jamais (je veux dire, un informaticien de base ne touchera jamais à autre
chose qu'à des processeurs de pc ou de serveur) n'est peut être pas utile
pour l'instant
Moi je t'avoue, j'en ai *marre* de corriger du code de debutant monte
en pousse qui me fout des void* dans des int
Je reformule: dan la vraie vie, on a souvent sizeof(void*) != sizeof(int), et
il est en effet important de le signaler (de même que sizeof(long) n'est pas
forcément >= sizeof(void*))
Dans le cas du sizeof((signed|unsigned) char), c'est tellement rare que dans
la pratique les quelques cas spécifiques (à la DSP, par exemple) seront de
toute manière tellement bien cadrés que cela ne posera pa de problèmes.
Plus tot le debutant prendra quelques bons reflexes, comme d'appeler un
chat un chat, mieux ca vaudra pour tout le monde.
D'un autre côté le surcharger avec des notions qu'il n'utilisera probablement
jamais (je veux dire, un informaticien de base ne touchera jamais à autre
chose qu'à des processeurs de pc ou de serveur) n'est peut être pas utile
pour l'instant
Moi je t'avoue, j'en ai *marre* de corriger du code de debutant monte
en pousse qui me fout des void* dans des int
Je reformule: dan la vraie vie, on a souvent sizeof(void*) != sizeof(int), et
il est en effet important de le signaler (de même que sizeof(long) n'est pas
forcément >= sizeof(void*))
Dans le cas du sizeof((signed|unsigned) char), c'est tellement rare que dans
la pratique les quelques cas spécifiques (à la DSP, par exemple) seront de
toute manière tellement bien cadrés que cela ne posera pa de problèmes.Plus tot le debutant prendra quelques bons reflexes, comme d'appeler un
chat un chat, mieux ca vaudra pour tout le monde.
D'un autre côté le surcharger avec des notions qu'il n'utilisera probablement
jamais (je veux dire, un informaticien de base ne touchera jamais à autre
chose qu'à des processeurs de pc ou de serveur) n'est peut être pas utile
pour l'instant
J'imagine que ces types ne sont proposés que sur des architectures dans
lesquelle ces caractéristiques sont natives. A l'exception des grandes
largeurs, par exemple un int64_t en x86-32 (les mots de 64 bits y sont
quand même efficacement supportés). J'ai quand même un doute, pour gcc
par exemple.
Personnellement, avant de découvrir les intN_t, je préférais (enfin,
quand j'étrais rigoureux) utiliser des typedef pour ne garder char que
pour des caractères (des lettres) et nommer de façon parlante selon le
sens, les types arithmétiques signés et non signés, et les "cases
mémoire" non signés.
Par exemple
typedef unsigned char octet_t;
typedef unsigned char uByte_t;
typedef unsigned char sByte_t;
J'imagine que ces types ne sont proposés que sur des architectures dans
lesquelle ces caractéristiques sont natives. A l'exception des grandes
largeurs, par exemple un int64_t en x86-32 (les mots de 64 bits y sont
quand même efficacement supportés). J'ai quand même un doute, pour gcc
par exemple.
Personnellement, avant de découvrir les intN_t, je préférais (enfin,
quand j'étrais rigoureux) utiliser des typedef pour ne garder char que
pour des caractères (des lettres) et nommer de façon parlante selon le
sens, les types arithmétiques signés et non signés, et les "cases
mémoire" non signés.
Par exemple
typedef unsigned char octet_t;
typedef unsigned char uByte_t;
typedef unsigned char sByte_t;
J'imagine que ces types ne sont proposés que sur des architectures dans
lesquelle ces caractéristiques sont natives. A l'exception des grandes
largeurs, par exemple un int64_t en x86-32 (les mots de 64 bits y sont
quand même efficacement supportés). J'ai quand même un doute, pour gcc
par exemple.
Personnellement, avant de découvrir les intN_t, je préférais (enfin,
quand j'étrais rigoureux) utiliser des typedef pour ne garder char que
pour des caractères (des lettres) et nommer de façon parlante selon le
sens, les types arithmétiques signés et non signés, et les "cases
mémoire" non signés.
Par exemple
typedef unsigned char octet_t;
typedef unsigned char uByte_t;
typedef unsigned char sByte_t;
Merci Xavier et Eric pour vos réponses rapides.
Ok, j'ai compris le << (décalage) et le | (ou logique). Mais pas trop
le & 0xff.
J'imagine que le &, c'est le "et", mais en quoi cela masque les 8 bits
de poids faible d'en entier?
J'ai trouver sous java que pour transformer un byte en entier on
utilise :
(buffer[0] & 0xff) | ((buffer[1] & 0xff) << 8) | ((buffer[2] & 0xff)
<< 16) | (buffer[3] << 24)
Pour moi, un byte, c'est 8 bits, donc un entier entre 0 et 255.
Un byte en C, c'est bien équivalement à un char?
Merci Xavier et Eric pour vos réponses rapides.
Ok, j'ai compris le << (décalage) et le | (ou logique). Mais pas trop
le & 0xff.
J'imagine que le &, c'est le "et", mais en quoi cela masque les 8 bits
de poids faible d'en entier?
J'ai trouver sous java que pour transformer un byte en entier on
utilise :
(buffer[0] & 0xff) | ((buffer[1] & 0xff) << 8) | ((buffer[2] & 0xff)
<< 16) | (buffer[3] << 24)
Pour moi, un byte, c'est 8 bits, donc un entier entre 0 et 255.
Un byte en C, c'est bien équivalement à un char?
Merci Xavier et Eric pour vos réponses rapides.
Ok, j'ai compris le << (décalage) et le | (ou logique). Mais pas trop
le & 0xff.
J'imagine que le &, c'est le "et", mais en quoi cela masque les 8 bits
de poids faible d'en entier?
J'ai trouver sous java que pour transformer un byte en entier on
utilise :
(buffer[0] & 0xff) | ((buffer[1] & 0xff) << 8) | ((buffer[2] & 0xff)
<< 16) | (buffer[3] << 24)
Pour moi, un byte, c'est 8 bits, donc un entier entre 0 et 255.
Un byte en C, c'est bien équivalement à un char?
Dans le cas du sizeof((signed|unsigned) char), c'est tellement rare que
dans la pratique les quelques cas spécifiques (à la DSP, par exemple)
seront de toute manière tellement bien cadrés que cela ne posera pa de
problèmes.
D'un autre côté le surcharger avec des notions qu'il n'utilisera
probablement jamais (je veux dire, un informaticien de base ne touchera
jamais à autre chose qu'à des processeurs de pc ou de serveur) n'est
peut être pas utile pour l'instant
Dans le cas du sizeof((signed|unsigned) char), c'est tellement rare que
dans la pratique les quelques cas spécifiques (à la DSP, par exemple)
seront de toute manière tellement bien cadrés que cela ne posera pa de
problèmes.
D'un autre côté le surcharger avec des notions qu'il n'utilisera
probablement jamais (je veux dire, un informaticien de base ne touchera
jamais à autre chose qu'à des processeurs de pc ou de serveur) n'est
peut être pas utile pour l'instant
Dans le cas du sizeof((signed|unsigned) char), c'est tellement rare que
dans la pratique les quelques cas spécifiques (à la DSP, par exemple)
seront de toute manière tellement bien cadrés que cela ne posera pa de
problèmes.
D'un autre côté le surcharger avec des notions qu'il n'utilisera
probablement jamais (je veux dire, un informaticien de base ne touchera
jamais à autre chose qu'à des processeurs de pc ou de serveur) n'est
peut être pas utile pour l'instant
J'ai trouver sous java que pour transformer un byte en entier on
utilise :
(buffer[0] & 0xff) | ((buffer[1] & 0xff) << 8) | ((buffer[2] & 0xff)
<< 16) | (buffer[3] << 24)
Estg-ce la même chose en C?
Et si oui, pourriez-vous m'expliquer cette syntaxe?
J'ai trouver sous java que pour transformer un byte en entier on
utilise :
(buffer[0] & 0xff) | ((buffer[1] & 0xff) << 8) | ((buffer[2] & 0xff)
<< 16) | (buffer[3] << 24)
Estg-ce la même chose en C?
Et si oui, pourriez-vous m'expliquer cette syntaxe?
J'ai trouver sous java que pour transformer un byte en entier on
utilise :
(buffer[0] & 0xff) | ((buffer[1] & 0xff) << 8) | ((buffer[2] & 0xff)
<< 16) | (buffer[3] << 24)
Estg-ce la même chose en C?
Et si oui, pourriez-vous m'expliquer cette syntaxe?
(buffer[0] & 0xff) | ((buffer[1] & 0xff) << 8) | ((buffer[2] & 0xff)
<< 16) | (buffer[3] << 24)
Déja, il faut savoir que cette représentation est en little endian (le
"petit bout", càd les octets de poids les plus faibles, sont en
premier) et ne sera pas toujours compatible selon les cas avec la
plate-forme voulue.
Disons que, dans des représentations réseau,
c'est effectivement le plus courant.
Sinon le "& 0xff" qui masque les 8 premiers bits ne sert pas à grand
chose (buffer[n] est déja sur 8 bits),
par contre un cast de chaque octet en uint avant le décalage me
parait sécurisant,
dans la mesure
où le type résultant d'un (unsigned char)<<n n'est pas à priori
forcément un int..
(buffer[0] & 0xff) | ((buffer[1] & 0xff) << 8) | ((buffer[2] & 0xff)
<< 16) | (buffer[3] << 24)
Déja, il faut savoir que cette représentation est en little endian (le
"petit bout", càd les octets de poids les plus faibles, sont en
premier) et ne sera pas toujours compatible selon les cas avec la
plate-forme voulue.
Disons que, dans des représentations réseau,
c'est effectivement le plus courant.
Sinon le "& 0xff" qui masque les 8 premiers bits ne sert pas à grand
chose (buffer[n] est déja sur 8 bits),
par contre un cast de chaque octet en uint avant le décalage me
parait sécurisant,
dans la mesure
où le type résultant d'un (unsigned char)<<n n'est pas à priori
forcément un int..
(buffer[0] & 0xff) | ((buffer[1] & 0xff) << 8) | ((buffer[2] & 0xff)
<< 16) | (buffer[3] << 24)
Déja, il faut savoir que cette représentation est en little endian (le
"petit bout", càd les octets de poids les plus faibles, sont en
premier) et ne sera pas toujours compatible selon les cas avec la
plate-forme voulue.
Disons que, dans des représentations réseau,
c'est effectivement le plus courant.
Sinon le "& 0xff" qui masque les 8 premiers bits ne sert pas à grand
chose (buffer[n] est déja sur 8 bits),
par contre un cast de chaque octet en uint avant le décalage me
parait sécurisant,
dans la mesure
où le type résultant d'un (unsigned char)<<n n'est pas à priori
forcément un int..