los - python lenguaje
¿Cómo hacer que el intérprete de Python maneje correctamente los caracteres que no son ASCII en las operaciones de cadena? (11)
Demasiado tarde para una respuesta, pero la cadena original estaba en UTF-8 y ''/ xc2 / xa0'' es UTF-8 para NO-BREAK SPACE. Simplemente descodifique la cadena original como s.decode(''utf-8'')
(/ xa0 se visualiza como un espacio cuando se decodifica incorrectamente como Windows-1252 o latin-1:
Ejemplo (Python 3)
s = b''6/xc2/xa0918/xc2/xa0417/xc2/xa0712''
print(s.decode(''latin-1'')) # incorrectly decoded
u = s.decode(''utf8'') # correctly decoded
print(u)
print(u.replace(''/N{NO-BREAK SPACE}'',''_''))
print(u.replace(''/xa0'',''-'')) # /xa0 is Unicode for NO-BREAK SPACE
Salida
6Â 918Â 417Â 712
6 918 417 712
6_918_417_712
6-918-417-712
Tengo una cadena que se ve así:
6Â 918Â 417Â 712
La manera clara de recortar esta cadena (como lo entiendo Python) es simplemente decir que la cadena está en una variable llamada s
, obtenemos:
s.replace(''Â '', '''')
Eso debería hacer el truco. Pero, por supuesto, se queja de que el carácter no-ASCII ''/xc2''
en el archivo blabla.py no está codificado.
Nunca pude entender cómo cambiar entre diferentes codificaciones.
Aquí está el código, realmente es el mismo que el anterior, pero ahora está en contexto. El archivo se guarda como UTF-8 en el bloc de notas y tiene el siguiente encabezado:
#!/usr/bin/python2.4
# -*- coding: utf-8 -*-
El código:
f = urllib.urlopen(url)
soup = BeautifulSoup(f)
s = soup.find(''div'', {''id'':''main_count''})
#making a print ''s'' here goes well. it shows 6Â 918Â 417Â 712
s.replace(''Â '','''')
save_main_count(s)
No va más allá de la s.replace
...
El siguiente código reemplazará todos los caracteres que no sean ASCII con signos de interrogación.
"".join([x if ord(x) < 128 else ''?'' for x in s])
Este es un truco sucio, pero puede funcionar.
s2 = ""
for i in s:
if ord(i) < 128:
s2 += i
Por lo que valía, mi juego de caracteres era utf-8
y yo había incluido la línea clásica " # -*- coding: utf-8 -*-
".
Sin embargo, descubrí que no tenía Newlines universales al leer estos datos desde una página web.
Mi texto tenía dos palabras, separadas por " /r/n
". Solo me estaba dividiendo en /n
reemplazando la "/n"
.
Una vez que hice un bucle y vi el personaje en cuestión, me di cuenta del error.
Por lo tanto, también podría estar dentro del juego de caracteres ASCII , pero un personaje que no esperabas.
Python 2 usa ascii
como la codificación predeterminada para los archivos de origen, lo que significa que debe especificar otra codificación en la parte superior del archivo para usar caracteres no unicos de ASCII en los literales. Python 3 usa utf-8
como la codificación predeterminada para los archivos fuente, por lo que este no es un problema.
Ver: http://docs.python.org/tutorial/interpreter.html#source-code-encoding
Para habilitar la codificación de fuente utf-8, esto iría en una de las dos líneas superiores:
# -*- coding: utf-8 -*-
Lo anterior está en los documentos, pero esto también funciona:
# coding: utf-8
Consideraciones adicionales:
El archivo de origen también se debe guardar usando la codificación correcta en su editor de texto.
En Python 2, el literal Unicode debe tener
u
antes, como ens.replace(u"Â ", u"")
Pero en Python 3, solo use comillas. En Python 2, puedefrom __future__ import unicode_literals
para obtener el comportamiento de Python 3, pero tenga en cuenta que esto afecta a todo el módulo actual.s.replace(u"Â ", u"")
también fallará sis
no es una cadena unicode.string.replace
devuelve una nueva cadena y no se edita en su lugar, así que asegúrese de estar usando el valor de retorno también
Sé que es un hilo viejo, pero me sentí obligado a mencionar el método de traducción, que siempre es una buena manera de reemplazar todos los códigos de caracteres por encima de 128 (u otros si es necesario).
Uso : str. traducir ( tabla [, deletechars] )
>>> trans_table = ''''.join( [chr(i) for i in range(128)] + ['' ''] * 128 )
>>> ''Résultat''.translate(trans_table)
''R sultat''
>>> ''6Â 918Â 417Â 712''.translate(trans_table)
''6 918 417 712''
A partir de Python 2.6 , también puede establecer la tabla en Ninguno, y usar deletechars para eliminar los caracteres que no desea, como en los ejemplos que se muestran en los documentos estándar en http://docs.python.org/library/stdtypes.html .
Con cadenas de caracteres unicode, la tabla de traducción no es una cadena de 256 caracteres, sino una expresión con el ord () de caracteres relevantes como claves. Pero de todos modos obtener una cadena ascii apropiada de una cadena Unicode es bastante simple, usando el método mencionado anteriormente por truppo, a saber: unicode_string.encode ("ascii", "ignorar")
Como resumen, si por alguna razón necesitas obtener una cadena de caracteres (por ejemplo, cuando levantas una excepción estándar con excepción de raise Exception, ascii_message
), puedes usar la siguiente función:
trans_table = ''''.join( [chr(i) for i in range(128)] + [''?''] * 128 )
def ascii(s):
if isinstance(s, unicode):
return s.encode(''ascii'', ''replace'')
else:
return s.translate(trans_table)
Lo bueno de la traducción es que puedes convertir los caracteres acentuados en caracteres ascii relevantes sin acentos, en lugar de simplemente eliminarlos o reemplazarlos por ''?''. Esto a menudo es útil, por ejemplo, para fines de indexación.
Usando Regex:
import re
strip_unicode = re.compile("([^-_a-zA-Z0-9!@#%&=,/''/";:~`/$/^/*/(/)/+/[/]/./{/}/|/?/</>//]+|[^/s]+)")
print strip_unicode.sub('''', u''6Â 918Â 417Â 712'')
#!/usr/bin/env python
# -*- coding: utf-8 -*-
s = u"6Â 918Â 417Â 712"
s = s.replace(u"Â", "")
print s
Esto imprimirá 6 918 417 712
>>> unicode_string = u"hello aåbäcö"
>>> unicode_string.encode("ascii", "ignore")
''hello abc''
def removeNonAscii(s): return "".join(filter(lambda x: ord(x)<128, s))
editar: mi primer impulso es usar siempre un filtro, pero la expresión del generador es más eficiente en cuanto a la memoria (y más corta) ...
def removeNonAscii(s): return "".join(i for i in s if ord(i)<128)
Tenga en cuenta que esto está garantizado para trabajar con la codificación UTF-8 (porque todos los bytes en caracteres de varios bytes tienen el bit más alto establecido en 1).
s.replace(u''Â '', '''') # u before string is important
y haga que su archivo .py
unicode.