Pergunta

eu tenho este:

>>> print 'example'
example
>>> print 'exámple'
exámple
>>> print 'exámple'.upper()
EXáMPLE

O que eu preciso fazer para imprimir:

EXÁMPLE

(Onde o 'a' recebe o seu sotaque accute, mas em letras maiúsculas.)

Eu estou usando Python 2.6.

Foi útil?

Solução

Eu acho que é tão simples como não a conversão para ASCII em primeiro lugar.

 >>> print u'exámple'.upper()
 EXÁMPLE

Outras dicas

Em 2.x do Python, apenas converter a string para unicode antes de chamar superior (). Usando o seu código, que está em formato UTF-8 sobre esta página web:

>>> s = 'exámple'
>>> s
'ex\xc3\xa1mple'  # my terminal is not utf8. c3a1 is the UTF-8 hex for á
>>> s.decode('utf-8').upper()
u'EX\xc1MPLE'  # c1 is the utf-16 aka unicode for á

A chamada para decode leva-lo de seu formato atual para unicode. Você pode, em seguida, convertê-lo para algum outro formato, como utf-8, usando codificação. Se o personagem era, digamos, iso-8859-2 (Checa, etc, neste caso), você iria passar a usar s.decode('iso-8859-2').upper().

Como no meu caso, se o seu terminal não é unicode / UTF-8 em conformidade, o melhor que você pode esperar é tanto uma representação hexadecimal dos personagens (como o meu) ou para convertê-lo lossily usando s.decode('utf-8').upper().encode('ascii', 'replace'), o que resulta em ' EX? mple'. Se você não pode fazer o seu show unicode terminal, escrever a saída para um arquivo no formato UTF-8 e aberto que no seu editor favorito.

Primeiro, eu só uso python 3.1 nos dias de hoje; o seu mérito central é ter cadeias de bytes disambiguated de objectos Unicode. isso faz com que a grande maioria das manipulações de texto muito mais seguro do que costumava ser o caso. pesando os trilhões de perguntas do usuário sobre problemas python 2.x codificação, a convenção u'äbc de python 2.1 foi apenas um erro; com bytes explícita e bytearray, a vida fica muito mais fácil.

Em segundo lugar, se Py3k não é o seu sabor, em seguida, tentar ir com from __future__ import unicode_literals, como o comportamento dessa vontade de Py3k mímico em python 2.6 e 2.7. essa coisa teria evitado o (facilmente comprometido) asneira que você fez ao dizer print 'exámple'.upper(). essencialmente, este é o mesmo que no Py3k: print( 'exámple'.encode( 'utf-8' ).upper() ). comparar estas versões (para Py3k):

print( 'exámple'.encode( 'utf-8' ).upper() )
print( 'exámple'.encode( 'utf-8' ).upper().decode( 'utf-8' ) )
print( 'exámple'.upper() )

O primeiro é, basicamente, o que você fez quando usou um 'exámple' corda nua, desde que você definir o seu padrão codificação para utf-8 (de acordo com um pronunciamento BDFL, estabelecendo o padrão de codificação em tempo de execução é uma má idéia, portanto, em PY2 você vai ter que enganá-lo, dizendo import sys; reload( sys ); sys.setdefaultencoding( 'utf-8' ); i apresentar uma solução melhor para Py3k abaixo). quando você olha para a saída destas três linhas:

b'EX\xc3\xa1MPLE'
EXáMPLE
EXÁMPLE

Você pode ver que quando upper() foi aplicado ao primeiro texto, ele agiu em bytes, não em caracteres. pitão permite que o método upper() em bytes, mas ela só é definido na interpretação US-ASCII de bytes. desde valores utf-8 utilizações in <> dentro 8 bits, mas fora de US-ASCII (128 até 255, que não são usados ??em US-ASCII), aqueles que não será afetados por upper(), então quando nós decodificar volta na segunda linha, temos que minúscula á. Finalmente, a terceira linha faz isso direito, e sim, surpresa, python parece estar ciente de que Á é a letra maiúscula correspondente a á. eu corri um teste rápido para ver o que personagens Python 3 não converter entre maiúsculas e minúsculas:

for cid in range( 3000 ):
  my_chr = chr( cid )
  if my_chr == my_chr.upper() and my_chr == my_chr.lower():
    say( my_chr )

folheando a lista revela muito poucas incidências de latino, cirílico, ou letras gregas; maior parte da produção é caracteres não-europeus e pontuação. os únicos personagens eu poderia achar que python foi errado são ? / ? (\ u0524, \ u0525, 'cirílico {capitais | small} carta pe com descender'), por isso, enquanto você ficar fora dos latino blocos estendida-X ( confira os, eles podem produzir surpresas), que você pode realmente usar esse método. Claro, eu não verificar a exatidão dos mapeamentos.

Por último, aqui é o que eu colocar em minha seção de inicialização aplicação Py3k: um método que redefine o sys.stdout codificação vê, com referências de caracteres numéricos (NCRs) como fallback; isso tem o efeito que a impressão para a saída padrão nunca vai levantar um erro de codificação Unicode. Quando eu trabalho no ubuntu, _sys.stdout.encoding é utf-8; quando o mesmo programa roda em Windows, que poderia ser algo singular como cp850. os olhares, Poder saída starnge, mas o aplicativo é executado sem levantar uma exceção nesses terminais witted-dim.

#===========================================================================================================
# MAKE STDOUT BEHAVE IN A FAILSAFE MANNER
#-----------------------------------------------------------------------------------------------------------
def _harden_stdout():
  """Ensure that unprintable output to STDOUT does not cause encoding errors; use XML character references
  so any kind of output gets a chance to render in a decipherable way."""
  global _sys_TRM
  _sys.stdout       = _sys_TRM = _sys_io.TextIOWrapper(
    _sys.stdout.buffer,
    encoding        = _sys.stdout.encoding,
    errors          = 'xmlcharrefreplace',
    line_buffering  = true )
#...........................................................................................................
_harden_stdout()

mais um conselho: ao testar, tente sempre print repr( x ) ou uma coisa semelhante que revela a identidade de x. todos os tipos de mal-entendidos podem surgir se você apenas print x em PY2 e x ou é um octeto string ou um objeto unicode. é muito intrigante e propenso a causar uma série de cabeça-arranhão. Como eu disse, tentar mover pelo menos a py26 com que a partir futuro literais importação unicode encantamento.

E para fechar, citando uma citação: "Glyph Lefkowitz diz que é melhor em seu artigo Encoding :

Eu acredito que, no contexto desta discussão, o termo "string" é sem significado. Há um texto, e há é Bdados orientada a YTE (o qual pode muito bem representar texto, mas ainda não é convertido para ele). Em tipos de Python, Texto é unicode. Dados é str. A ideia de "texto não-Unicode" é apenas um erro esperando para acontecer de programação. "

atualização: acabou de encontrar python 3 corretamente convertidos s LATIN PEQUENA longa carta S para S quando maiúscula. puro!

Eu acho que há um pouco de fundo que estamos perdendo aqui:

>>> type('hello')
<type 'str'>

>>> type(u'hello')
<type 'unicode'>

Enquanto você estiver usando cordas "Unicode" em vez de cordas "nativos", os operadores gosto superior () irá operar com unicode em mente. FWIW, Python 3 usa Unicode por padrão, fazendo a distinção em grande parte irrelevante.

Como tirar uma seqüência de unicode para str e depois voltar para unicode é abaixo do ideal em muitos aspectos, e muitas bibliotecas irá produzir saída unicode se quiser; de modo a tentar usar apenas objetos unicode para cordas internamente sempre que puder.

Experimente:

s = 'exámple'
print unicode(s).upper()
Licenciado em: CC-BY-SA com atribuição
Não afiliado a StackOverflow
scroll top