2012-05-23 2 views
5

Possible en double:
Size of character ('a') in C/C++Opérateur sizeof C/C++: Pourquoi sizeof ('a') renvoie-t-il des valeurs différentes?

Je suis un débutant à C, et a été confondu par cela.

C: J'ai essayé d'imprimer le sizeof ('a') en C en utilisant le modificateur "% zu", et il imprime une valeur 4.

C++: Impression sizeof ('a') en C++ en utilisant Cout, et printf (en utilisant le format ci-dessus) a imprimé une valeur 1.

Je crois que la valeur correcte devrait être 1, puisque 'a' sera pris comme un caractère. Pourquoi ne retourne-t-il pas 4 en C? Les tailles des opérations des deux sont-elles différentes dans les deux langues? Si oui, quelle est la différence et pourquoi renvoie-t-elle une valeur différente? J'ai utilisé les compilateurs gcc dans les deux cas.

+7

Parce que C n'est pas C++. Ne pas essayer d'être sarcastique ici. Vous ne seriez probablement pas surpris si un caractère dans C était différent d'un caractère dans Python, mais beaucoup de gens pensent que C est simplement un sous-ensemble de C++. Pas du tout le cas. Les bonnes réponses ci-dessous, mais l'essentiel est que C et C++ sont 2 langues différentes. – Dan

Répondre

11

En C, la 'a' est une constante de caractère, traitée comme un entier, vous obtenez donc une taille de 4, alors qu'en C++ elle est traitée comme char. Ceci est un double de la question ici:

Size of character ('a') in C/C++

+0

J'avais essayé de chercher, mais cela ne correspondait à aucune question. Merci de me le faire savoir. –

+0

-1: Il n'y a pas de définition en C de la taille d'un Int au-delà de sa taille par rapport à char et long. – mattnz

+3

@mattnz - Si vous lisez la réponse liée, vous pouvez voir clairement dans les commentaires (de la première et de la seule réponse) que 'sizeof' un' int' dépend de la plateforme. Je n'ai pas abordé ce problème parce que 1. le thread lié l'adresse et je m'attends à un mod pour fermer ce 2. thread et compte tenu du contexte de la question du demandeur, clairement la taille d'un int est 4 sur sa machine. – BlackJack

4

En C un caractère littéral (constante) est du type int. Alors, tenez compte du programme

#include <stdio.h> 

main(int argc, char *argv[]) 
{ 
    printf("%zu\n", sizeof('a')); 
    printf("%zu\n", sizeof('ab')); 
    printf("%zu\n", sizeof('abc')); 
    printf("%zu\n", sizeof('abcd')); 

    printf("%u\n", 'a'); 
    printf("%u\n", 'ab'); 
    printf("%u\n", 'abc'); 
    printf("%u\n", 'abcd'); 

    printf("%x\n", 'a'); 
    printf("%x\n", 'ab'); 
    printf("%x\n", 'abc'); 
    printf("%x\n", 'abcd'); 

    printf("%c\n", 'a'); 
    printf("%c\n", 'ab'); 
    printf("%c\n", 'abc'); 
    printf("%c\n", 'abcd'); 
} 

Les quatre premières déclarations considèrent tous les littéraux comme un caractère constant suivant et ils ont tous l'impression 4 == SizeF (int), au moins sur gcc (Ubuntu 4.4.3 4ubuntu5.1) 4.4.3. Notez que ce compilateur imprime plusieurs avertissements pour le programme ci-dessus:

warning: multi-character character constant 

En fait, un caractère littéral spécifie les quatre octets constituant un int, de gauche à droite, l'octet d'ordre supérieur en premier. Les manquants principaux octets sont remplis de 0. Donc, sur ma machine le deuxième et le troisième groupe de printf imprimer

97 
24930 
6382179 
1633837924 
61 
6162 
616263 
61626364 

Dans la sortie hexadécimale vous voyez la disposition des quatre personnages dans le littéral (le Codes ASCII de gauche à droite): le 'a' est mappé au octet le plus fort 0x61).

Enfin, le quatrième groupe de tirages:

a 
b 
c 
d 

à-dire les caractères littéraux sont poussés sur la pile sous forme d'entiers, mais printf imprime seulement l'octet le plus bas de cette int comme un produit de carbonisation. C++ se comporte d'une manière similaire, mais les littéraux caractères d'un octet sont considérés comme de type char, pas int. Le programme

#include <iostream> 

using namespace std; 

main(int argc, char *argv[]) 
{ 
    cout << sizeof('a') << endl; 
    cout << sizeof('ab') << endl; 
    cout << sizeof('abc') << endl; 
    cout << sizeof('abcd') << endl; 

    cout << 'a' << endl; 
    cout << 'ab' << endl; 
    cout << 'abc' << endl; 
    cout << 'abcd' << endl; 
} 

compilera en utilisant GCC et donner un avertissement similaire.Sa sortie est différente de celle de C:

1 
4 
4 
4 
a 
24930 
6382179 
1633837924 

donc caractère un octet littéraux sont traités comme char, tandis que littéraux multi-octets sont traités comme int.

NOTE IMPORTANTE

J'ai couru mes tests sur un système Linux 32 bits sur lequel un int a 4 octets. Ce serait intéressant de voir ce qui se passe sur d'autres systèmes, par ex. sur un système 64 bits.

EDIT

réponse fixe (merci pour l'indice): caractères littéraux sont de type int en C, ils ne sont pas jeté int.

+0

La plupart des systèmes ont 4 octets 'int', sauf ceux de 16 bits. –

+1

Petite erreur: les constantes de caractères ne sont pas converties en 'int', elles ont _have_ type' int' en C. –

+0

Merci, je vais corriger cela. Cela signifie qu'ils sont castés en char chaque fois qu'ils sont assignés. – Giorgio