Différence entre UTF-8 et UTF-16?

Différence entre UTF-8 et UTF-16? Pourquoi en avons-nous besoin?

MessageDigest md = MessageDigest.getInstance("SHA-256"); Ssortingng text = "This is some text"; md.update(text.getBytes("UTF-8")); // Change this to "UTF-16" if needed byte[] digest = md.digest(); 

Je crois qu’il y a beaucoup de bons articles à ce sujet sur le Web, mais voici un bref résumé.

UTF-8 et UTF-16 sont des codages de longueur variable. Cependant, dans UTF-8, un caractère peut occuper un minimum de 8 bits, tandis que dans UTF-16, la longueur des caractères commence par 16 bits.

Principaux pros UTF-8:

  • Les caractères ASCII de base tels que les chiffres, les caractères latins sans accent, etc. occupent un octet identique à la représentation US-ASCII. De cette manière, toutes les chaînes US-ASCII deviennent valides UTF-8, ce qui offre une compatibilité descendante décente dans de nombreux cas.
  • Aucun octet nul, ce qui permet d’utiliser des chaînes terminées par un caractère nul, cela introduit également une grande compatibilité avec les versions antérieures.
  • UTF-8 est indépendant de l’ordre des octets, vous n’avez donc pas à vous soucier du problème Big Endian / Little Endian.

Contre UTF-8 principal:

  • Beaucoup de caractères courants ont des longueurs différentes, ce qui ralentit l’indexation par codepoint et le calcul d’un décompte de points de code terriblement.
  • Même si l’ordre des octets n’a pas d’importance, parfois, UTF-8 a toujours une BOM (marque d’ordre des octets) qui sert à notifier que le texte est encodé en UTF-8 et à la compatibilité avec le logiciel ASCII même si . Les logiciels Microsoft (comme Notepad) aiment particulièrement append BOM à UTF-8.

Principaux pros de l’UTF-16:

  • Caractères BMP (Basic Multilingual Plane), dont le latin, le cyrillique, le plus de chinois (le PRC prend en charge certains points de code en dehors de BMP obligatoires), la plupart des japonais peuvent être représentés avec 2 octets. Cela accélère l’indexation et le calcul du nombre de points de code dans le cas où le texte ne contient pas de caractères supplémentaires.
  • Même si le texte comporte des caractères supplémentaires, ils sont toujours représentés par des paires de valeurs 16 bits, ce qui signifie que la longueur totale est toujours divisible par deux et permet d’utiliser le caractère 16 bits comme composant primitif de la chaîne.

Contre UTF-16 principal:

  • Beaucoup d’octets nuls dans les chaînes US-ASCII, ce qui signifie pas de chaînes terminées par un caractère nul et beaucoup de mémoire gaspillée.
  • L’utiliser comme un codage de longueur fixe «fonctionne principalement» dans de nombreux scénarios courants (en particulier aux États-Unis / UE / pays avec alphabet cyrillique / Israël / pays arabes / Iran et bien d’autres), conduisant souvent à un échec. Cela signifie que les programmeurs doivent être conscients des paires de substitution et les gérer correctement dans les cas où cela est important!
  • Sa longueur étant variable, le comptage ou l’indexation des points de code est coûteux, bien que inférieur à UTF-8.

En général, UTF-16 est généralement préférable pour la représentation en mémoire car BE / LE n’y est pas pertinent (il suffit d’utiliser l’ordre natif) et l’indexation est plus rapide (n’oubliez pas de gérer correctement les paires de substitution). UTF-8, d’autre part, est extrêmement utile pour les fichiers texte et les protocoles réseau car il n’y a pas de problème avec BE / LE et la terminaison null est souvent utile, tout comme la compatibilité ASCII.

Ce sont simplement des schémas différents pour représenter les caractères Unicode.

Les deux sont de longueur variable – UTF-16 utilise 2 octets pour tous les caractères dans le plan multilingue de base (BMP) qui contient la plupart des caractères couramment utilisés.

UTF-8 utilise entre 1 et 3 octets pour les caractères du BMP, jusqu’à 4 pour les caractères de la plage Unicode actuelle de U + 0000 à U + 1FFFFF, et est extensible jusqu’à U + 7FFFFFFF si cela devient nécessaire … mais notamment tous les caractères ASCII sont représentés dans un seul octet chacun.

Pour les besoins d’un message, le choix ne sera pas important, à condition que tous ceux qui essaient de recréer le résumé utilisent la même option.

Voir cette page pour en savoir plus sur UTF-8 et Unicode.

(Notez que tous les caractères Java sont des points de code UTF-16 dans le BMP; pour représenter les caractères au-dessus de U + FFFF, vous devez utiliser des paires de substitution en Java.)

Ceci n’est pas lié à UTF-8/16 (en général, bien qu’il soit converti en UTF16 et que la partie BE / LE puisse être définie avec une seule ligne), le moyen le plus rapide de convertir Ssortingng en octet []. Par exemple: bon exactement pour le cas fourni (code de hachage). Ssortingng.getBytes (enc) est relativement lent.

 static byte[] toBytes(Ssortingng s){ byte[] b=new byte[s.length()*2]; ByteBuffer.wrap(b).asCharBuffer().put(s); return b; } 

Un moyen simple de différencier UTF-8 et UTF-16 consiste à identifier les points communs entre eux.

Outre le partage du même numéro Unicode pour un caractère donné, chacun est leur propre format.