Ascii, Ansi et Unicode | Unicode et UTF-8 | La voie de la facilité
Caractères Unicode et caractères UTF-8
Il existe souvent une confusion entre les caractères Unicode et les caractères UTF-8. Le mieux est de comprendre le principe (relativement simple) qui sous-tend les deux systèmes. Les solutions adoptées pour afficher lettres accentuées et caractères chinois deviennent alors évidentes.
Ascii, Ansi et Unicode
L'unité de base de la mémoire d'ordinateur est depuis très longtemps l'octet, ou nombre binaire de 8 bits. L'octet permet de stocker 2 puissance 8 nombres, soit 256 nombres numérotés de 0 à 255. Le contenu de l'octet peut être interprété de différentes façons: on peut le considérer comme un véritable nombre, comme l'adresse d'une variable, ou comme le numéro d'élément d'un ensemble. Dans le cas qui nous intéresse, l'octet représente le numéro rattaché à un caractère.
La table Ansi est codée sur un octet (ou 8 bits) et permet donc de faire référence à 256 caractères différents. Les caractères Ansi ont été choisis de façon arbitraire, même si leur ordre suit une certaine logique. Ces caractères sont très largement répandus depuis 1990, notamment sur les PC. Ils permettent de codifier l'essentiel des langues d'Europe de l'ouest, avec malheureusement quelques oublis comme le œ. À titre d'exemple, dans la table Ansi, l'octet valant 65 (ou 0100 0001) correspond à la lettre A, l'octet 66 (ou 0100 0010) à la lettre B, l'octet 97 (0110 0001) à la lettre a et l'octet 233 (ou 1110 1001) à la lettre é.
Le « bogue » de l'an 2000 n'est qu'un exemple de la vieille ferraille qui encombre l'informatique. Pour économiser quelques bits, on avait par exemple remplacé l'année 1968 par 68, en espérant mourir avant le siècle suivant. Le même phénomène s'est produit pour les caractères. Aux États-Unis, le 8e bit de l'octet a été sacrifié très tôt pour des fins techniques (il servait à vérifier la qualité d'une transmission) ou économiques (cela raccourcissait le temps de transmission). Comme la seule lettre accentuée utilisée en anglais est le é, on l'abandonna sans remords. À l'époque, l'informatique servait à faire des calculs et non de la dentelle. La table Ascii rassemble les 128 caractères codés sur 7 bits (puisque 2 puissance 7 = 128). La table Ascii est un sous-ensemble de la table Ansi, c'est-à-dire que les 128 premiers caractères des deux tables sont identiques.
Notons que les vénérables télétypes utilisaient des caractères codés sur 5 bits (soit 32 combinaisons). Ces bits étaient nettement visibles sous forme de petits trous sur les étroites bandes de papier qui servaient de mémoire à ces machines. C'était une sorte de code Morse amélioré, et l'économie gagnée sur le nombre de bits par caractère était raisonnable dans les circonstances.
L'humanité ne se limitant pas à l'Europe de l'Ouest et ses rejetons, on se sentit vite à l'étroit dans les 256 caractères de la table Ansi. D'où l'apparition des caractères à 16 bits, ou caractères Unicode, numérotés de 0 à 65535 (puisque 2 puissance 16 = 65536). La table Unicode englobe les tables précédentes: les 256 premiers caractères Unicode équivalent aux 256 caractères Ansi (qui sont eux-mêmes une extension de la table Ascii). Plusieurs dizaines d'alphabets on été insérés dans la table Unicode, notamment le grec (931 = Σ) le cyrillique (1046 = Ж), l'arabe (1578 = ت), le devanagari (2336 = ठ), le hiragana (12353 = ぁ), les caractères sino-japonais (de 19968 = 一 à 40869 = 龥) et bien d'autres. La table Unicode se veut universelle, c'est-à-dire qu'une seule et unique table répond aux besoins de tous les peuples.
Il faut noter que si la table Unicode est déjà bien intégrée dans de nombreux langages de programmation, les simples utilisateurs ont souvent recours, sans même le savoir, à des codages qui varient d'un pays à l'autre. Ainsi, la fameuse table Guobiao, ou GB2312 (République populaire de Chine) fonctionne comme la table Unicode, excepté que l'ordre des caractères est différent, pour des raisons historiques. Dans ce cas, il suffit heureusement d'un tableau de correspondance pour passer de l'Unicode au Guobiao et vice-versa. Cependant, la table Guobiao ne contient pas tous les caractères Unicode: les caractères chinois simplifiés y sont inclus, mais pas les caractères européens accentués (du moins, pas dans la table originale). Cette table est donc incompatible avec le français.
Les tables Ascii, Ansi et Unicode sont des standards reconnus et répandus. On peut considérer qu'Ansi est la table de base (codée sur un octet, comme la mémoire de l'ordinateur): Ascii est alors un Ansi appauvri ou archaïque, et Unicode un Ansi élargi ou moderne. Rien ne justifie théoriquement de conserver trois standards. Idéalement, il faudrait adopter Unicode et se débarrasser des autres tables, avec leurs économies de bouts de chandelle dérisoires sur les giga-systèmes actuels. D'ailleurs, Unicode commence lui aussi à se sentir à l'étroit et on se dirige vers un codage à 4 octets qui devrait régler la question une fois pour toute.
Comment concilier les trois systèmes: Unicode et UTF-8
Objectif
S'il est logique et avantageux de se débarrasser des anciens standards pour laisser la place à l'Unicode, cela va cependant à l'encontre de « l'irrationalité économique » (c'est un des principes méconnus de l'économie moderne!). Pour permettre aux vieux fossiles de continuer à ignorer le reste de l'humanité, et surtout de ne pas mettre à jour tous leurs vieux documents, il fallait trouver une solution de « compromis ». C'est le système UTF-8, qui laisse les utilisateurs de l'anglais (table Ascii) fonctionner comme si l'Unicode n'existait pas, tout en permettant (avec quelques frustrations, d'où ce pénible article) au reste du monde d'utiliser sa propre langue.
Principe
Le système UTF-8 est moins une table qu'une façon de lire une table. Lorsqu'on lit un caractère UTF-8, on doit d'abord reconnaître s'il s'agit d'un simple caractère Ascii. Si oui, la question est réglée. Dans le cas contraire on doit examiner le ou les octets suivants pour compléter l'information nécessaire au calcul du numéro Unicode du caractère. On peut donc considérer que les caractères UTF-8 sont des caractères Unicode camouflés ou transformés. Voyons maintenant comment obtenir le caractère Unicode qui se cache derrière le voile de l'UTF-8.
Mise en œuvre
Si l'octet UTF-8 lu a une valeur comprise entre 0 et 127, c'est un caractère Ascii. On reconnaît ce caractère au fait que son bit supérieur est toujours égal à 0:
— 0XXX XXXX (où X représente un nombre binaire: 0 ou 1).
Si le bit supérieur est égal à 1, alors deux cas se présentent:
— 110X XXXX: le caractère est codé sur deux octets; l'octet suivant a la forme 10XX XXXX; on colle les 11 bits significatifs (représentés ici par des X) afin d'obtenir un nombre compris entre 0 et 2047 (puisque 2 puissance 11 = 2048).
— 111? XXXX: le caractère est codé sur trois octets; les octets suivants ont la forme 10XX XXXX et 10XX XXXX; on colle les 16 bits significatifs (4 + 6 + 6) afin d'obtenir un nombre compris entre 0 et 65535.
Note: dans les exemples ci-dessus, l'ensemble des bits codés X sert à déterminer la valeur Unicode des caractères UTF-8; les bits codés 0 ou 1 servent à identifier la méthode de calcul de cette valeur; le bit codé ? n'est pas utilisé.
Exemples
Codage sur 2 octets: La lettre Ansi é (233 = 1110 1001) devient UTF-8 é (195 + 169 ou 1100 0011 + 1010 1001 = 000 1110 1001).
Codage sur 3 octets:
Le caractère Unicode 一 [yī: un] (19968 = 0100 1110 0000 0000) devient UTF-8 一 (228 + 184 + 128 ou 1110 0100 + 1011 1000 + 1000 0000 = 0100 1110 0000 0000).
Quels sont ces misérables 德?
La ligne ci-dessus est écrite en UTF-8. Les caractères é représentent tout simplement la lettre é (UTF-8 à deux octets) et les caractères å¾· représentent le chinois 德 (UTF-8 à trois octets). Les autres lettres ne sont pas affectées puisqu'elles font partie de la table Ascii (caractères à 7 bits). Lorsqu'on écrit en UTF-8, il faut en informer le destinataire (ici le Navigateur), sinon celui-ci traitera les caractères en utilisant les paramètres de langue de la page Web, ou de l'ordinateur. La page que vous êtes en train de lire contient l'instruction (invisible) charset=iso-8859-1 qui demande au Navigateur de traiter les caractères selon la table Ansi (ou ISO ou Latin-1). Pour être correctement affichés à destination, votre page Web ou votre courriel codés en UTF-8 doivent aussi contenir une telle instruction, par exemple: charset=utf-8.
Conclusion
En attendant l'universalisation de l'Unicode ou de son successeur étendu, le système UTF-8 sert de dénominateur commun aux différents systèmes de codage. Tous les codages peuvent être convertis vers l'UTF-8 ou depuis l'UTF-8. En ce sens l'UTF-8 est l'Esperanto du codage des caractères. Malheureusement, l'UTF-8 élimine les caractères accentués tels que nous les connaissons (exemple: é devient é) ce qui oblige les non-anglophones à avoir recours à un éditeur spécialisé.
Pour ne pas se compliquer la vie: la troisième voie
Beaucoup d'utilisateurs de courriel et de forums s'arrachent les cheveux avec les différents types de codage. En désespoir de cause, ils se servent de la méthode essai-erreur en passant des codages UTF-8 à Europe occidentale (Ansi) ou Guobiao, etc.. Après quelques aller-retour, le message devient illisible et personne ne se rappelle ce qu'il a fait. Nous espérons que cette page leur aura permis, non pas de se lancer dans des calculs binaires, mais simplement d'y voir plus clair.
Quant à ceux qui créent des pages Web à l'aide d'un éditeur de texte ordinaire, ils ont un moyen bien simple de combiner caractères Ascii, lettres françaises accentuées et caractères chinois, sans se préoccuper du système UTF-8. L'entête de la page contiendra l'instruction charset=iso-8859-1, ce qui permettra de taper directement en français (à l'exception du œ). Pour introduire un caractère Unicode (supérieur à 255), on suivra le modèle nnnnn; dans lequel nnnnn est remplacé par le numéro du caractère Unicode en question.
Exemples:
彭 = 彭 (caractère chinois)
ī = ī (caractère pinyin)
œ = œ (caractère français)
Renaud Bouret - 2002