O Que É Codificação Unicode?
Unicode é um padrão universal de codificação de caracteres que atribui um número único — chamado ponto de código — a cada caractere usado nas línguas humanas. Antes do Unicode, existiam dezenas de sistemas de codificação incompatíveis. Um documento escrito em russo num sistema era ilegível noutro. O Unicode resolve isto fornecendo um conjunto de caracteres único e unificado que cobre mais de 150 scripts e 140.000 caracteres.
O Unicode em si não é uma codificação. É um repertório de caracteres. A camada de codificação — como os pontos de código são armazenados como bytes — é tratada por formas de codificação como UTF-8, UTF-16 e UTF-32. Compreender a distinção entre um ponto de código e a sua representação em bytes é a chave para evitar erros de codificação.
Pontos de Código
Cada caractere Unicode tem um ponto de código escrito como U+ seguido de um número hexadecimal. A letra A é U+0041, o símbolo do euro é U+20AC, e o emoji 😀 é U+1F600.
Os pontos de código estão organizados em 17 planos, cada um contendo 65.536 caracteres. O primeiro plano (Plano 0) é o Plano Multilingue Básico (BMP), que contém os caracteres mais comuns incluindo Latim, Grego, Cirílico, CJK e muitos outros. Os Planos 1 a 16 contêm caracteres suplementares como emojis, scripts históricos e caracteres CJK raros.
| Plano | Intervalo | Nome |
|---|---|---|
| 0 | U+0000 a U+FFFF | Plano Multilingue Básico (BMP) |
| 1 | U+10000 a U+1FFFF | Plano Multilingue Suplementar (SMP) |
| 2 | U+20000 a U+2FFFF | Plano Ideográfico Suplementar (SIP) |
| 3-13 | U+30000 a U+DFFFF | Não atribuídos |
| 14 | U+E0000 a U+EFFFF | Plano Suplementar de Propósito Especial (SSP) |
| 15-16 | U+F0000 a U+10FFFF | Planos de Uso Privado |
UTF-8, UTF-16, UTF-32
Estas três formas de codificação diferem em como mapeiam pontos de código para bytes.
UTF-8
UTF-8 é a codificação dominante na web. Usa 1 a 4 bytes por caractere e é retrocompatível com ASCII. Caracteres no intervalo ASCII (U+0000 a U+007F) usam um byte. Scripts europeus usam dois bytes. Caracteres CJK e emojis usam três ou quatro bytes.
| Intervalo de Ponto de Código | Byte 1 | Byte 2 | Byte 3 | Byte 4 |
|---|---|---|---|---|
| U+0000 - U+007F | 0xxxxxxx | |||
| U+0080 - U+07FF | 110xxxxx | 10xxxxxx | ||
| U+0800 - U+FFFF | 1110xxxx | 10xxxxxx | 10xxxxxx | |
| U+10000 - U+10FFFF | 11110xxx | 10xxxxxx | 10xxxxxx | 10xxxxxx |
Vantagens do UTF-8:
- Texto ASCII é UTF-8 válido (sem necessidade de conversão)
- Auto-sincronização: pode sempre encontrar limites de caracteres
- Sem problemas de ordem de bytes (little-endian / big-endian)
- Mais eficiente em espaço para texto em script latino
UTF-16
UTF-16 usa 2 bytes (uma unidade de código) para caracteres BMP e 4 bytes (duas unidades de código, chamadas pares suplentes) para caracteres suplementares. Windows, Java e JavaScript usam UTF-16 internamente.
UTF-16 tem problemas de ordem de bytes. Um ficheiro UTF-16 deve especificar se é little-endian (UTF-16LE) ou big-endian (UTF-16BE), tipicamente usando um BOM (Byte Order Mark) no início.
UTF-32
UTF-32 usa exatamente 4 bytes para cada ponto de código. É simples mas desperdiçador. Um ficheiro puramente ASCII torna-se quatro vezes maior. UTF-32 raramente é usado na prática.
Comparação
| Característica | UTF-8 | UTF-16 | UTF-32 |
|---|---|---|---|
| Bytes por caractere | 1-4 | 2 ou 4 | 4 |
| Compatibilidade ASCII | Sim | Não | Não |
| Uso na web | ~98% | ~2% | <0.01% |
| BOM necessário | Não | Sim | Sim |
| Comum em | Web, Linux, JSON | Windows, Java, JS | Processamento interno |
Erros de Codificação
O erro de codificação mais comum é tratar bytes como caracteres. Quando pega numa string UTF-8 e a interpreta como Latin-1 (ISO 8859-1), caracteres acentuados aparecem como símbolos distorcidos. Isto acontece quando a codificação não é declarada ou quando uma ferramenta assume a codificação errada.
Outro problema comum é contar bytes em vez de caracteres. Em UTF-8, a string "café" tem 4 caracteres mas 5 bytes porque é usa dois bytes. Funções como strlen do PHP contam bytes por padrão, enquanto mb_strlen conta caracteres.
Exemplos de Programação
// PHP - use sempre funções mb_* para UTF-8
$text = 'café ☕';
echo strlen($text); // 8 bytes (contagem errada)
echo mb_strlen($text, 'UTF-8'); // 6 caracteres
// Codificar/descodificar pontos de código Unicode
echo mb_convert_encoding($text, 'UTF-16', 'UTF-8');
# Python 3 - strings são Unicode por padrão
text = 'café ☕'
print(len(text)) # 6 caracteres
bytes_utf8 = text.encode('utf-8')
bytes_utf16 = text.encode('utf-16')
print(bytes_utf8) # b'caf\xc3\xa9 \xe2\x98\x95'
// JavaScript - strings são UTF-16 internamente
let text = 'café ☕';
console.log(text.length); // 6 (mas emoji pode contar como 2)
// Codificar como bytes UTF-8
let encoder = new TextEncoder();
let bytes = encoder.encode(text);
console.log(bytes); // Uint8Array(8)
Ferramenta Online
A ferramenta Unicode Encoder & Decoder no Help2Code converte texto para pontos de código Unicode e entre representações UTF-8, UTF-16 e UTF-32. É útil para depurar problemas de codificação e aprender como o Unicode funciona.
Conclusão
A codificação Unicode é conhecimento essencial para qualquer desenvolvedor que trabalhe com texto internacional. UTF-8 é o padrão para a web e deve ser a sua escolha padrão. Compreender a diferença entre pontos de código e representações em bytes ajudá-lo-á a evitar os erros de codificação de texto mais comuns. Use o Unicode Encoder & Decoder para experimentar codificações e depurar problemas de codificação.