parse.unquote_plus TypeError
Question
Je suis en train de formater un fichier afin qu'il puisse être inséré dans une base de données, le fichier est compressé à l'origine et arround 1.3MB grand. Chaque ligne ressemble à ceci:
398% + 001% 7EAnoniem 7E, 543,480,7525010,1775,0
Voici comment le code ressemble à ce fichier qui parse:
Village = gzip.open(Root+'\\data'+'\\' +str(Newest_Date[0])+'\\' +str(Newest_Date[1])+'\\' +str(Newest_Date[2])\
+'\\'+str(Newest_Date[3])+' village.gz');
Village_Parsed = str
for line in Village:
Village_Parsed = Village_Parsed + urllib.parse.unquote_plus(line);
print(Village.readline());
Quand je lance le programme que je reçois cette erreur:
Village_Parsed = Village_Parsed + urllib.parse.unquote_plus(line);
fichier "C: \ Python31 \ lib \ urllib \ parse.py", ligne 404, en unquote_plus string = String.replace ( '+', ' « ) TypeError: un objet prévu à l'interface de la mémoire tampon
Toute idée de ce qui ne va pas ici? Merci d'avance pour toute aide:)
La solution
import gzip, os, urllib.parse
archive_relpath = os.sep.join(map(str, Newest_Date[:4])) + ' village.gz'
archive_path = os.path.join(Root, 'data', archive_relpath)
with gzip.open(archive_path) as Village:
Village_Parsed = ''.join(urllib.parse.unquote_plus(line.decode('ascii'))
for line in Village)
print(Village_Parsed)
Sortie:
398,~Anoniem 001~,543,480,7525010,1775,0
NOTE: RFC 3986 - Uniform Resource Identifier (URI): Syntaxe générique dit:
Cette spécification ne pas tout codage de caractères particulier pour le mappage entre les caractères URI et les octets utilisés pour stocker ou transmettre ces caractères. Lorsqu'un URI apparaît dans un élément de protocole, le codage de caractères est définie par ce que protocole; sans une telle définition, un URI est supposé être en le codage de caractères de la texte qui l'entoure.
Par conséquent 'ascii'
dans le fragment de line.decode('ascii')
doit être remplacé par quelque encodage que vous avez utilisé pour encoder votre texte.
Autres conseils
PROBLÈME 1 est que urllib.unquote_plus n'aime pas le line
que vous avez nourri. Le message doit être « S'il vous plaît fournir un objet str » :-) Je vous suggère de résoudre le problème 2 ci-dessous, et insérer:
print('line', type(line), repr(line))
immédiatement après votre déclaration de for
afin que vous puissiez voir ce que vous obtenez dans line
.
Vous trouverez qu'il retourne octets objets:
>>> [line for line in gzip.open('test.gz')]
[b'nudge nudge\n', b'wink wink\n']
En utilisant un mode de 'r' a un effet peu:
>>> [line for line in gzip.open('test.gz', 'r')]
[b'nudge nudge\n', b'wink wink\n']
Je suggère qu'au lieu de passer line
à la routine d'analyse syntaxique vous passez line.decode('UTF-8')
... ou quel que soit le codage utilisé lorsque le fichier gz a été écrit.
PROBLEME 2 se trouve dans cette ligne:
Village_Parsed = str
str
est un type. Vous avez besoin d'un objet vide str. Pour obtenir cela, vous pouvez appeler le type à savoir str()
qui est formellement correcte mais peu pratique / inhabituelle / scoffable / bizarre par rapport à l'utilisation d'une chaîne ''
constante ... donc faire ceci:
Village_Parsed = ''
Vous avez également PROBLÈME 3: votre dernière déclaration tente de lire le fichier gz après EOF
.