Por que o Apache Commons considera '१२३' numérico?


101

De acordo com a documentação do Apache Commons Lang para StringUtils.isNumeric(), a String '१२३' é numérica.

Como acreditei que isso poderia ser um erro na documentação, fiz testes para verificar a declaração. Descobri que, de acordo com o Apache Commons, é numérico.

Por que essa string é numérica? O que esses personagens representam?


61
Talvez eles representem dígitos em algum idioma. Nem todos os idiomas usam os símbolos de 0 a 9 para representar dígitos.
Eran de

165
estes são 1, 2 e 3 em hindi
Blip

11
Você pode obter o valor inteiro por Integer.parseInt("१२३").
saka1029 de

9
@ dan04 Esses não são números, são letras populares para representar constantes particulares. Observe a diferença entre ⅯⅭe MC.
gerrit

Respostas:


198

Porque aquele "CharSequence contém apenas dígitos Unicode" (citando sua documentação vinculada ).

Todos os caracteres retornam verdadeiros para Character.isDigit:

Alguns intervalos de caracteres Unicode que contêm dígitos:

  • '\ u0030' a '\ u0039', dígitos ISO-LATIN-1 ('0' a '9')
  • '\ u0660' a '\ u0669', dígitos árabe-índicos
  • '\ u06F0' a '\ u06F9', dígitos Árabe-Índico estendidos
  • '\ u0966' a '\ u096F', dígitos Devanágari
  • '\ uFF10' a '\ uFF19', dígitos de largura total

Muitos outros intervalos de caracteres também contêm dígitos.

१२३ são dígitos Devanágari:


11
Bem @Joker_vD, você não tenha especificado qual sobrecarga, então sim, com certeza: Integer.parseInt("222", 2).
Andy Turner de

4
@Joker_vD Não é nem difícil; existem muitos idiomas sem suporte. Mesmo assim, há o Chinise 亿, que representa 10 ^ 8 -> isto à potência de 3 causaria um estouro. Lista de sistemas numéricos
Cedric Reichenbach,

13
@CedricReichenbach: A principal diferença é que, embora 亿 seja numérico (pelos padrões de ter um dos valores não-Nenhum de Numeric_Type, neste caso Numeric_Type = Numeric), não é qualquer tipo de dígito . (Mesmo se fosse, você não o levaria à potência de 3; você aumentaria a raiz para várias potências, não os dígitos .) parseIntRequer dígitos, e talvez de forma confusa, o isNumericmétodo nesta questão testa caracteres de dígitos decimais ( General_Category = Decimal_Number) em vez de qualquer categoria mais ampla de caracteres numéricos.
user2357112 suporta Monica de

10
O conjunto completo de dígitos Devangari é ०१२३४५६७८९.
dan04 de

2
@ v7d8dpo4 (s) ele perguntou se havia uma maneira Integer.parseInt()de lançar uma exceção para uma string de entrada numérica de 3 caracteres.
Andy Turner,

59

O símbolo १२३ é o mesmo que 123 para o idioma nepalês ou qualquer outro idioma que use a escrita Devanagari , como hindi, gujarati e assim por diante e, portanto, é um número para o Apache Commons.


3
Essa coisa quase se parece com "123" em algarismos arábicos.
Panzercrisis

41
Os árabes receberam seus numerais dos indianos.

5
Os números árabes @rahul são de 1 a 9, não ١-٩ como comumente se pensa.
Março,

26

Você pode usar Character#getTypepara verificar a categoria geral do personagem:

System.out.println(Character.DECIMAL_DIGIT_NUMBER == Character.getType('१'));

Isso será impresso true, o que é uma "evidência" de que '१' é um número de dígito .

Agora vamos examinar o valor unicode do caractere '१':

System.out.println(Integer.toHexString('१'));
// 967

Esse número está na faixa dos dígitos Devanágari - que é: \u0966a \u096F.

Tente também:

Character.UnicodeBlock block = Character.UnicodeBlock.of('१');
System.out.println(block.toString());
// DEVANAGARI

Devanágari é:

é um alfabeto abugida (alfasilabário) da Índia e do Nepal

"१२३" é um "123" (Unicode latino básico).

Lendo:


1
É mais significativo que sejam do tipo DECIMAL_DIGIT_NUMBERdo que do DEVANAGARIbloco. Também há letras sem dígitos nesse bloco.
Andy Turner de

23

Se você quiser saber quais propriedades um determinado "caractere" possui (e existem alguns), vá diretamente para a fonte: Unicode.org . Eles têm ferramentas de pesquisa que podem mostrar quase tudo que você gostaria de saber.

TENHA EM MENTE: O Unicode Consortium produz uma especificação, não um software. Isso significa que cabe a cada fornecedor de software implementar a especificação com a maior precisão possível . Assim, assim como HTML, JavaScript, CSS, SQL, etc., há variação entre diferentes plataformas, linguagens e assim por diante. Por exemplo, encontrei um bug no .NET Framework da Microsoft em que as letras latinas circuladas A-Ze a-z- os pontos de código 0x24B6 a 0x24E9 - não são registrados corretamente como sendo char.IsLetter = true( relatório do bug aqui ). E isso leva a um comportamento inesperado na funcionalidade relacionada, como ao chamar o TextInfo.ToTitleCase()método ( relatório de bug aqui ).


1
Ótimas referências! (Embora eles me façam pensar se o Unicode passou do
limite

1
Se você quiser ter esse tipo de referência disponível localmente, pode instalar o uniprops .
TRiG

2
@TRiG Obrigado por mencionar isso. Utilidade interessante. Ele cobre algumas das funcionalidades mostradas nos primeiros 3 links (o conjunto original), mas acabei de atualizar minha resposta para incluir alguns links adicionais que mostram consultas mais avançadas que podem ser feitas em Unicode.org que não vejo possíveis via uniprops. Além disso, parece que unipropsestá uma versão atrás, visto que o Unicode lançou a versão 9.0 em junho passado.
Solomon Rutzky

19

Os símbolos '१२३' são, na verdade, derivados da língua hindi (basicamente da língua sânscrita, ou seja, Devanagiri), que representam valores numéricos como:

१ representa 1

२ representa 2

e como sábio


4
CORREÇÃO: Os símbolos '१२३' são, na verdade, derivados do idioma sânscrito (ou seja, a escrita Devanagiri, como outros pôsteres notaram)
Happy Green Kid Naps

Fiquei surpreso ao saber como recentemente Devanāgarī assumiu sua forma atual - muitos séculos depois que o sânscrito foi codificado! Portanto, sou cético quanto à afirmação de que os dígitos pertencem mais ao sânscrito do que à cultura indiana em geral.
Anton Sherwood,
Ao utilizar nosso site, você reconhece que leu e compreendeu nossa Política de Cookies e nossa Política de Privacidade.
Licensed under cc by-sa 3.0 with attribution required.