Si dans une situation donnée, vous avez un tableau de caractères (se terminant bien sûr par le caractère nul) et juste après, dans la position immédiatement suivante en mémoire, vous souhaitez stocker 0
en tant qu'int non signé, comment l'ordinateur fait-il la différence entre ces deux?
29
pic X occurs m to n depending on v
( et le décompte peut être n'importe où, pas juste avant), mais le stocker est plus compliqué.Réponses:
Ce n'est pas le cas.
Le terminateur de chaîne est un octet contenant tous les 0 bits.
L'int entier non signé est de deux ou quatre octets (selon votre environnement) contenant chacun les 0 bits.
Les deux articles sont stockés à des adresses différentes. Votre code compilé effectue des opérations adaptées aux chaînes sur le premier emplacement et des opérations adaptées aux nombres binaires non signés sur le dernier. (Sauf si vous avez soit un bug dans votre code, soit un code dangereusement intelligent!)
Mais tous ces octets sont identiques pour le processeur. Les données en mémoire (dans la plupart des architectures de jeux d'instructions courantes) ne sont associées à aucun type. C'est une abstraction qui n'existe que dans le code source et ne signifie que pour le compilateur.
Édition ajoutée: à titre d'exemple: il est parfaitement possible, même courant, d'effectuer une arithmétique sur les octets qui composent une chaîne. Si vous avez une chaîne de caractères ASCII 8 bits, vous pouvez convertir les lettres de la chaîne entre les majuscules et les minuscules en ajoutant ou en soustrayant 32 (décimal). Ou si vous traduisez vers un autre code de caractère, vous pouvez utiliser leurs valeurs comme indices dans un tableau dont les éléments fournissent le codage binaire équivalent dans l'autre code.
Pour le CPU, les caractères sont vraiment des entiers extra-courts. (huit bits chacun au lieu de 16, 32 ou 64.) Pour nous, les humains, leurs valeurs sont associées à des caractères lisibles, mais le CPU n'en a aucune idée. Il ne sait rien non plus sur la convention "C" de "l'octet nul termine une chaîne" (et comme beaucoup l'ont noté dans d'autres réponses et commentaires, il existe des environnements de programmation dans lesquels cette convention n'est pas utilisée du tout) .
Certes, certaines instructions en x86 / x64 sont généralement utilisées avec des chaînes - le préfixe REP par exemple - mais vous pouvez tout aussi bien les utiliser sur un tableau d'entiers, si elles atteignent le résultat souhaité.
la source
En bref, il n'y a pas de différence (sauf qu'un int fait 2 ou 4 octets de large et un char juste 1).
Le fait est que toutes les bibliothèques modernes utilisent la technique de terminaison nulle ou stockent la longueur d'une chaîne. Et dans les deux cas, le programme / ordinateur sait qu'il a atteint la fin d'une chaîne lorsqu'il a lu un caractère nul ou qu'il a lu autant de caractères que la taille le lui indique.
Problèmes avec ce démarrage lorsque le terminateur nul est manquant ou que la longueur est incorrecte, car alors le programme commence à lire à partir de la mémoire, il n'est pas censé le faire.
la source
Il n'y a pas de différence. Le code machine (assembleur) n'a pas de types variables, mais le type des données est déterminé par l'instruction.
Un meilleur exemple serait
int
etfloat
, si vous avez 4 octets en mémoire, il n'y a aucune information quant à savoir si c'est unint
ou unfloat
(ou quelque chose d'autre entièrement), mais il y a 2 instructions différentes pour l'addition entière et l'addition flottante, donc si l'ajout entier l'instruction est utilisée sur les données, alors c'est un entier, et vice versa.De même pour les chaînes, si vous avez du code qui, par exemple, regarde une adresse et compte les octets jusqu'à ce qu'elle atteigne un
\0
octet, vous pouvez la considérer comme une fonction calculant la longueur de la chaîne.Bien sûr, une programmation comme celle-ci serait une folie complète, c'est pourquoi nous avons des langages de niveau supérieur qui compilent directement du code machine et presque personne dans l'assembleur.
la source
La réponse scientifique en un seul mot serait: métadonnées.
Les métadonnées indiquent à l'ordinateur si certaines données à un certain emplacement sont un entier, une chaîne, un code de programme ou autre. Ces métadonnées peuvent faire partie du code du programme (comme l'a mentionné Jamie Hanrahan) ou elles peuvent être explicitement stockées quelque part.
Les processeurs modernes peuvent souvent distinguer les régions de mémoire affectées au code de programme et les régions de données (par exemple, le bit NX https://en.wikipedia.org/wiki/NX_bit ). Certains matériels exotiques peuvent également faire la distinction entre les chaînes et les nombres, oui. Mais le cas habituel est que le logiciel s'occupe de ce problème, que ce soit par des métadonnées implicites (dans le code) ou des métadonnées explicites (les machines virtuelles orientées objet stockent souvent les métadonnées (informations de type / classe) dans le cadre des données (objet)) .
Un avantage de ne pas faire la distinction entre différents types de données est que certaines opérations deviennent très simples. Le sous-système d'E / S n'a pas nécessairement besoin de savoir si les données qu'il lit ou écrit sur le disque sont en fait du code de programme, du texte lisible par l'homme ou des nombres. Ce ne sont que des morceaux qui sont transportés à travers la machine. Laissez le code du programme gérer les problèmes de frappe fantaisie.
la source
Ce n'est pas le cas. Tu le fais!
Ou votre compilateur / interprète.
Si les instructions indiquent à l'ordinateur d'ajouter le
0
sous forme de nombre, il le fera. S'ils disent à l'ordinateur d'arrêter d'imprimer les données après avoir atteint le0
, en tant que «caractère»\0'
, il le fera.Les langues ont des mécanismes pour garantir la façon de traiter les données. En C, les variables ont des types, comme
int
,float
etchar
, et le compilateur génère les bonnes instructions pour chaque type de données. Mais C vous permet de convertir des données d'une variable en une autre variable de type différent, même un pointeur peut être utilisé comme un nombre. Pour l'ordinateur, ce sont tous des bits comme les autres.la source
Un caractère nul est un octet et un entier non signé est deux octets.
la source