As funções de classificação padrão em quase todas as linguagens de programação são pouco adequadas para consumo humano. O que quero dizer com isso? Bem, considere a diferença entre classificar nomes de arquivos no Windows Explorer e classificar esses mesmos nomes de arquivos por meio do Array.Sort()
código:
Classificação do shell do Explorer | Array.Sort()
|
![]() |
![]() |
É uma grande diferença.
Posso dizer, sem o menor sinal de exagero, que o senhor esse exato problema de classificação tem sido um ponto sensível em todos os projetos em que já trabalhei. Os usuários inevitavelmente reclamam que seus itens não estão sendo classificados corretamente e apresentam bugs sobre esses “erros”. Sendo membros de carteirinha do clube homo logicus, nós, programadores, soltamos um suspiro cansado e tentamos controlar qualquer revirada de olhos óbvia enquanto informamos pacientemente aos nossos usuários que este não é um erro. Itens são ordenados na ordem correta. Adequada ASCII ou seja, a ordem. Enquanto nos afastamos, esperamos que o senhor não nos ouça murmurando baixinho o que realmente estamos pensando: “Usuários estúpidos! Eles nem sequer entendem como funciona a classificação!”
Sempre senti uma pontada de arrependimento ao rejeitar essas solicitações. Sinceramente, veja essas duas listas… que pessoa sã gostaria de uma ordem ASCII? É uma ordenação completamente sem sentido para qualquer pessoa que não tenha o gráfico ASCII gravada na memória (e, a propósito, A maiúsculo é 65 decimal). Nunca entendi realmente que havia outra maneira de classificar, embora a classificação natural estivesse bem à nossa frente o tempo todo, na forma de listagens de arquivos do Mac Finder e do Windows Explorer. Eu usava antolhos induzidos pelo idioma. Se o nosso sort
retorna em ordem ASCII, então isso deve estar correto. Ele nos foi legado pelos Deuses da Linguagem. Pode haver haver de outra forma?
Kate Rhodes está um pouco irritada com a nossa ignorância coletiva sobre ASCIIbetical vs. Alphabetical. Não posso dizer que a culpo. Sou tão culpado quanto os outros. Afinal, os usuários não eram os mais estúpidos. Eu era.
Por bobagem minha, achei que a classificação alfabética era uma necessidade tão comum (a julgar pelo número de pessoas que perguntam como fazer isso, também não estou errado) que não precisaria escrever essa maldita coisa. Mas eu não contava com o fator estupidez. Jesus Cristo, pessoal. Os senhores são programadores. Quase todos os senhores têm diploma universitário e nenhum deles sabe o que significa “Alfabético”. Todos os senhores deveriam ter vergonha. Se algum dos senhores estiver usando o algoritmo de classificação padrão da sua linguagem, que é quase certo que seja ASCIIbetical (por um bom motivo) para obter a classificação alfabética, dirija-se ao espelho mais próximo e dê um tapa em si mesmo repetidamente antes de voltar às suas mesas e corrigir os testes de unidade que não detectaram esse problema.
Não é chamado de “Alphabetical sort” (classificação alfabética); é conhecido coletivamente como classificação natural. Mas ela tem razão em uma coisa: é difícil encontrar informações sobre a classificação natural, e muitos programadores a desconhecem completamente. Nenhuma das linguagens de computador comuns (que eu saiba) implementa nada além da classificação ASCIIbética. No entanto, há alguns lugares onde o senhor pode encontrar algoritmos de classificação natural:
Não se deixe enganar pela inteligente linha de dez do Python de Ned. A implementação de uma classificação natural é mais complexa do que parece, e não apenas para o o i18n maligno que mencionei acima. Mas as implementações do Python são impressionantemente sucintas. Um dos comentaristas de Ned postou esta versão, que é ainda mais curta:
import re def sort_nicely( l ): """ Sort the given list in the way that humans expect. """ convert = lambda text: int(text) if text.isdigit() else text alphanum_key = lambda key: [ convert(c) for c in re.split('([0-9]+)', key) ] l.sort( key=alphanum_key )
Tentei criar uma implementação inteligente e igualmente sucinta da classificação natural em C# 3.0, mas não consegui. Não estou interessado em um concurso de uma linha, necessariamente, mas me parece que uma classificação natural básica não deveria exigir as mais de 40 linhas de código necessárias na maioria das linguagens.
Como programadores, seria bom que tivéssemos em mente a lição de Kate: ASCIIbetical não é igual a alfabético. A classificação ASCII atende às necessidades do computador e do compilador, mas e quanto a nós, seres humanos? Talvez uma opção de classificação natural mais amigável ao ser humano deva ser incorporada às principais linguagens de programaçãotambém.