1. O que é unicode?
O Unicode se originou de uma idéia muito simples: incluir todos os personagens do mundo em uma coleção. Enquanto o computador suportar esse conjunto de caracteres, ele poderá exibir todos os caracteres e não haverá código iluminado novamente.
Começa em 0 e especifica um número para cada símbolo, que é chamado de "ponto CodePoint". Por exemplo, o símbolo do ponto de código 0 é nulo (indica que todos os bits binários são 0).
Copie o código da seguinte forma: u+0000 = nulo
Na fórmula acima, U+ significa que o número hexadecimal imediatamente após o ponto de código do Unicode.
Atualmente, a versão mais recente do Unicode é a versão 7.0, com um total de 109.449 símbolos, dos quais 74.500 estão incluídos em caracteres chineses, japoneses e coreanos. Pode-se acreditar aproximadamente que mais de dois terços dos símbolos existentes no mundo vêm de personagens do Leste Asiático. Por exemplo, o ponto de código para o "bom" chinês é hexadecimal 597D.
Copie o código da seguinte forma: u+597d = ok
Com tantos símbolos, o Unicode não é definido ao mesmo tempo, mas a definição de partição. Cada área pode armazenar 65.536 (216) caracteres, chamada de avião. Atualmente, existem 17 (25) aviões no total, o que significa que o tamanho de todo o conjunto de caracteres Unicode é agora 221.
Os primeiros 65536 bits de caracteres são chamados de plano básico (BMP abreviado) e seus pontos de código variam de 0 a 216-1. Escrito em hexadecimal é de u+0000 a u+ffff. Todos os caracteres mais comuns são colocados neste plano, que é o primeiro plano que o Unicode define e publica.
Os caracteres restantes são colocados no plano auxiliar (SMP abreviado) e os pontos de código variam de U+010000 a U+10FFFF.
2. UTF-32 e UTF-8
Unicode especifica apenas o ponto de código de cada caractere. Que tipo de ordem de bytes é usada para representar esse ponto de código, que envolve o método de codificação.
O método de codificação mais intuitivo é que cada ponto de código é representado por quatro bytes, e o conteúdo de bytes corresponde ao ponto de código um por um. Esse método de codificação é chamado UTF-32. Por exemplo, o ponto 0 de código é representado por quatro bytes de 0, e o ponto de código 597D é adicionado com dois bytes de 0 na frente.
Copie o código da seguinte forma: U+0000 = 0x0000 0000U+597D = 0x0000 597D
A vantagem do UTF-32 é que as regras de conversão são simples e intuitivas e a eficiência da pesquisa é alta. A desvantagem é que é desperdiçado espaço e o texto em inglês com o mesmo conteúdo será quatro vezes maior que a codificação ASCII. Essa desvantagem é fatal, resultando em ninguém realmente usando esse método de codificação. O padrão HTML5 estipula explicitamente que as páginas da Web não devem ser codificadas no UTF-32.
O que as pessoas realmente precisam é um método de codificação que salva espaço, que levou ao nascimento do UTF-8. O UTF-8 é um método de codificação de comprimento de variável, com comprimentos de caracteres que variam de 1 byte a 4 bytes. Quanto mais comumente usados caracteres, mais curtos os bytes. Os primeiros 128 caracteres são representados por apenas 1 byte, o que é exatamente o mesmo que o código ASCII.
Faixa de número bytes 0x0000 - 0x007F10X0080 - 0x07FF20X0800 - 0XFFF30X010000 - 0X10FFFF4
Devido ao recurso de economia de espaço da UTF-8, ele se tornou a codificação da Web mais comum na Internet. No entanto, tem pouco a ver com o tópico de hoje, então não vou entrar nisso. Para o método de transcodificação específico, consulte "Notas de codificação de personagens" que escrevi há muitos anos.
Iii. Introdução ao UTF-16
A codificação UTF-16 está entre UTF-32 e UTF-8 e combina as características de dois métodos de codificação: comprimento fixo e comprimento variável.
Suas regras de codificação são simples: os caracteres no plano básico ocupam 2 bytes e os caracteres no plano auxiliar ocupam 4 bytes. Ou seja, o comprimento da codificação do UTF-16 é de 2 bytes (u+0000 a u+ffff) ou 4 bytes (u+010000 a u+10ffff).
Portanto, há uma pergunta: quando encontramos dois bytes, como vemos que é um personagem em si ou precisamos interpretá -lo com os outros dois bytes?
É muito inteligente, e eu não sei se foi intencional. No plano básico, do U+D800 ao U+DFFF é um segmento vazio, ou seja, esses pontos de código não correspondem a nenhum caractere. Portanto, esse segmento vazio pode ser usado para mapear os caracteres do plano auxiliar.
Especificamente, existem 220 bits de caracteres no plano auxiliar, o que significa que pelo menos 20 bits binários são necessários para esses caracteres. O UTF-16 divide esses 20 bits ao meio. Os primeiros 10 bits são mapeados em U+D800 para U+DBFF (tamanho do espaço 210), que é chamado de bit alto (H), e os últimos 10 bits são mapeados em U+DC00 para U+DFFF (tamanho 210 do espaço), que é chamado de bit baixo (L). Isso significa que um caráter de um plano auxiliar é dividido em dois planos básicos de representações de caráter.
Portanto, quando encontramos dois bytes e descobrimos que seu ponto de código está entre U+D800 e U+DBFF, podemos concluir que o ponto de código imediatamente após os dois bytes deve estar entre U+DC00 e U+DFFF. Esses quatro bytes devem ser interpretados juntos.
4. Fórmula de transcodificação de UTF-16
Ao converter o código Unicode para UTF-16, primeiro distingue se esse é um caractere plano básico ou um caractere plano auxiliar. Se for o primeiro, converta diretamente o ponto de código para a forma hexadecimal correspondente, com um comprimento de dois bytes.
Copie o código da seguinte forma: U+597D = 0x597D
Se for um caractere plano auxiliar, o Unicode versão 3.0 fornece uma fórmula de transcodificação.
Copie o código do código da seguinte forma: h = math.floor ((c -0x10000) / 0x400) + 0xd800l = (c - 0x10000) % 0x400 + 0xdc00
Tomando um personagem como exemplo, é um caractere plano auxiliar com um ponto de código U+1d306. O processo de cálculo de convertê-lo para UTF-16 é o seguinte.
Copie o código do código da seguinte maneira: h = math.floor ((0x1d306-0x10000)/0x400)+0xd800 = 0xd834l = (0x1d306-0x10000) % 0x400+0xdc00 = 0xdf06
Portanto, a codificação UTF-16 do caractere é 0xd834 DF06, com um comprimento de quatro bytes.
5. Qual codificação é usada em JavaScript?
A linguagem JavaScript usa conjuntos de caracteres Unicode, mas suporta apenas um método de codificação.
Essa codificação não é UTF-16, nem UTF-8, nem UTF-32. O JavaScript não usa os métodos de codificação acima.
O JavaScript usa UCS-2!
Vi. Codificação UCS-2
Por que um UCS-2 apareceu de repente? Isso requer um pouco de história.
Na época em que a Internet ainda não havia aparecido, havia duas equipes que queriam criar um conjunto de personagens unificado. Uma é a equipe Unicode criada em 1988, e a outra é a equipe da UCS criada em 1989. Quando descobriram a existência um do outro, eles rapidamente chegaram a um acordo: não há necessidade de dois conjuntos de personagens unificados no mundo.
Em outubro de 1991, as duas equipes decidiram mesclar o conjunto de personagens. Em outras palavras, apenas um conjunto de conjuntos de caracteres será lançado a partir de agora, que é Unicode, e os conjuntos de caracteres lançados anteriormente serão revisados, e os pontos de código do UCS serão exatamente os mesmos que o Unicode.
O progresso do desenvolvimento do UCS é mais rápido que o Unicode. Em 1990, foi anunciado o primeiro método de codificação UCS-2, usando 2 bytes para representar caracteres com pontos de código. (Naquela época, havia apenas um avião, que era o plano básico, então 2 bytes foram suficientes.) A codificação do UTF-16 não foi anunciada até julho de 1996, e foi claramente anunciado que era um superconjunto do UCS-2, ou seja, os caracteres de avião básicos foram codificados pelo Metoduhed By UCS-2 e os caracteres do plano auxiliar de 4 bytes.
Simplificando, a relação entre os dois é que o UTF-16 substitui o UCS-2 ou UCS-2 é integrado ao UTF-16. Então, agora existe apenas UTF-16, não UCS-2.
7. O fundo de nascimento do JavaScript
Então, por que o JavaScript não escolhe o UTF-16 mais avançado, mas usa o UCS-2 já obsoleto?
A resposta é muito simples: não é que você não queira, é que não pode. Porque quando a linguagem JavaScript apareceu, não havia codificação UTF-16.
Em maio de 1995, Brendan Eich projetou a linguagem JavaScript em 10 dias; Em outubro, o primeiro mecanismo de explicação foi lançado; Em novembro do ano seguinte, o Netscape enviou oficialmente os padrões de idiomas à ECMA (consulte "O nascimento do JavaScript" para obter detalhes sobre todo o processo). Ao comparar a data de lançamento do UTF-16 (julho de 1996), você entenderá que o Netscape não tinha outra escolha naquele momento, apenas o método de codificação UCS-2 estava disponível!
8.
Como o JavaScript pode lidar apenas com a codificação UCS-2, todos os caracteres são 2 bytes nesse idioma. Se tiverem 4 bytes, eles serão tratados como dois bytes duplos. As funções de personagem de JavaScript são afetadas por isso e não podem retornar o resultado correto.
Tome caracteres como exemplo, sua codificação UTF-16 é de 4 bytes 0xd834df06. O problema é que a codificação de 4 bytes não pertence ao UCS-2, e o JavaScript não o reconhece e o considerará apenas como dois caracteres separados u+d834 e u+df06. Como mencionado anteriormente, esses dois pontos de código estão vazios, portanto, o JavaScript os considerará as cordas compostas por dois caracteres vazios!
O código acima indica que o JavaScript acredita que o comprimento do caractere é 2, o primeiro caractere obtido é um caractere nulo e o ponto de código do primeiro caractere obtido é 0xdb34. Esses resultados não estão corretos!
Para resolver esse problema, você deve julgar o ponto do código e ajustá -lo manualmente. A seguir, é a maneira correta de escrever uma string.
Copie o código do código da seguinte forma: while (++ Índice <length) {// ... if (charcode> = 0xd800 && charcode <= 0xdbff) {output.push (caractere+string.charat (++ index)); } else {output.push (caractere); }}
O código acima indica que, ao atravessar a string, você deve julgar o ponto de código. Desde que caia no intervalo entre 0xd800 e 0xdbff, ele deve ser lido junto com os próximos 2 bytes.
Problemas semelhantes existem em todas as funções de manipulação de caracteres JavaScript.
String.prototype.replace ()
String.prototype.substring ()
String.prototype.slice ()
...
Todas as funções acima são válidas apenas para pontos de código de 2 bytes. Para processar corretamente os pontos de código de 4 bytes, você deve implantar sua própria versão um por um e julgar o intervalo de pontos do código do caractere atual.
9. ECMAScript 6
A próxima versão do JavaScript, ECMAScript 6 (ES6 para abreviação), aprimorou bastante o suporte do Unicode, basicamente resolvendo esse problema.
(1) identificar corretamente os caracteres
O ES6 pode reconhecer automaticamente pontos de código de 4 bytes. Portanto, é muito mais fácil atravessar as cordas.
Copie o código da seguinte forma: para (deixe s de string) {// ...}
No entanto, para manter a compatibilidade, o atributo de comprimento ainda é o comportamento original. Para obter o comprimento correto da string, você pode usar o seguinte método.
Copie o código da seguinte forma: Array.From (String) .Length
(2) representação do ponto de código
O JavaScript permite que os caracteres Unicode sejam representados diretamente com os pontos de código, que são escritos como "pontos de código de backslash + U +".
Copie o código da seguinte forma: 'ok' === '/u597d' // true
No entanto, essa notação é inválida para pontos de código de 4 bytes. O ES6 corrigiu esse problema e pode identificá -lo corretamente, desde que os pontos de código sejam colocados em aparelhos encaracolados.
(3) Função de processamento de string
O ES6 adicionou várias novas funções que lidam especificamente com pontos de código de 4 bytes.
String.FromCodePoint (): retornar o caractere correspondente do ponto de código Unicode
String.prototype.codePointat (): retornar o ponto de código correspondente do caractere
String.prototype.at (): retorna o personagem na posição especificada da string
(4) Expressão regular
O ES6 fornece o modificador U para adicionar pontos de código de 4 bytes a expressões regulares.
(5) regularização unicode
Alguns caracteres têm símbolos adicionais, além das letras. Por exemplo, no pinyin chinês, o tom na letra é um símbolo adicional. Os símbolos de tom são muito importantes para muitos idiomas europeus.
O Unicode fornece dois métodos de representação. Um é um caractere único com símbolos adicionais, ou seja, um ponto de código representa um caractere, como o ponto de código de ǒ é u+01d1; O outro é usar o símbolo adicional como um ponto de código e exibi -lo em combinação com o caractere principal, ou seja, dois pontos de código representam um caractere, como ǒ pode ser escrito como O (u+004f)+ˇ (u+030c).
Copie o código da seguinte forma: // Método 1 '/u01d1' // 'ǒ' // Método 2 '/u004f/u030c' // 'ǒ'
Esses dois métodos de representação são exatamente os mesmos em visão e semântica e devem ser tratados como situações equivalentes. No entanto, o JavaScript não pode dizer.
Copie o código da seguinte forma: '/u01d1' === '/u004f/u030c' // false
O ES6 fornece um método normalizado, permitindo "regularização unicode", ou seja, convertendo os dois métodos na mesma sequência.
Copie o código da seguinte
Para mais introdução ao ES6, consulte "Entretenimento do ECMAScript 6".