J'essaie de lire et d'écrire une trame de données dans un fichier délimité par des tuyaux. Certains caractères sont des lettres non romaines (`, ç, ñ, etc.). Mais ça casse quand j'essaie d'écrire les accents en ASCII.
df = pd.read_csv('filename.txt',sep='|', encoding='utf-8')
<do stuff>
newdf.to_csv('output.txt', sep='|', index=False, encoding='ascii')
-------
File "<ipython-input-63-ae528ab37b8f>", line 21, in <module>
newdf.to_csv(filename,sep='|',index=False, encoding='ascii')
File "C:\Users\aliceell\AppData\Local\Continuum\Anaconda3\lib\site-packages\pandas\core\frame.py", line 1344, in to_csv
formatter.save()
File "C:\Users\aliceell\AppData\Local\Continuum\Anaconda3\lib\site-packages\pandas\formats\format.py", line 1551, in save
self._save()
File "C:\Users\aliceell\AppData\Local\Continuum\Anaconda3\lib\site-packages\pandas\formats\format.py", line 1652, in _save
self._save_chunk(start_i, end_i)
File "C:\Users\aliceell\AppData\Local\Continuum\Anaconda3\lib\site-packages\pandas\formats\format.py", line 1678, in _save_chunk
lib.write_csv_rows(self.data, ix, self.nlevels, self.cols, self.writer)
File "pandas\lib.pyx", line 1075, in pandas.lib.write_csv_rows (pandas\lib.c:19767)
UnicodeEncodeError: 'ascii' codec can't encode character '\xb4' in position 7: ordinal not in range(128)
Si je change to_csv pour avoir un encodage utf-8, alors je ne peux pas lire le fichier correctement:
newdf.to_csv('output.txt',sep='|',index=False,encoding='utf-8')
pd.read_csv('output.txt', sep='|')
> UnicodeDecodeError: 'utf-8' codec can't decode byte 0xb4 in position 2: invalid start byte
Mon objectif est d'avoir un fichier délimité par des tuyaux qui conserve les accents et les caractères spéciaux.
De plus, existe-t-il un moyen simple de déterminer sur quelle ligne read_csv se casse? Pour le moment, je ne sais pas comment l'obtenir pour me montrer le (s) mauvais caractère (s).
Vous avez des caractères qui ne sont pas ASCII et ne peuvent donc pas être encodés comme vous essayez de le faire. J'utiliserais simplement utf-8
comme suggéré dans un commentaire.
Pour vérifier quelles lignes sont à l'origine du problème, vous pouvez essayer quelque chose comme ceci:
def is_not_ascii(string):
return string is not None and any([ord(s) >= 128 for s in string])
df[df[col].apply(is_not_ascii)]
Vous devrez spécifier la colonne col
que vous testez.
Vérifiez la réponse ici
C'est une solution beaucoup plus simple:
newdf.to_csv("C:/tweetDF", sep='\t', encoding = 'utf-8')
Une autre solution consiste à utiliser les fonctions de chaîne encoder/décoder avec l'option 'ignorer', mais cela supprimera les caractères non ascii:
df['text'] = df['text'].apply(lambda x: x.encode('ascii', 'ignore').decode('ascii'))