web-dev-qa-db-fra.com

Le fichier CSV écrit en Python a des lignes vides entre chaque ligne

import csv

with open('thefile.csv', 'rb') as f:
  data = list(csv.reader(f))
  import collections
  counter = collections.defaultdict(int)

  for row in data:
        counter[row[10]] += 1


with open('/pythonwork/thefile_subset11.csv', 'w') as outfile:
    writer = csv.writer(outfile)
    for row in data:
        if counter[row[10]] >= 504:
           writer.writerow(row)

Ce code lit thefile.csv, apporte des modifications et écrit les résultats dans thefile_subset1.

Cependant, lorsque j'ouvre le csv résultant dans Microsoft Excel, il y a une ligne vierge supplémentaire après chaque enregistrement!

Y a-t-il un moyen de ne pas mettre une ligne vierge supplémentaire?

En Python 2, ouvrez outfile avec le mode 'wb' au lieu de 'w'. Le csv.writer écrit le \r\n directement dans le fichier. Si vous n'ouvrez pas le fichier en mode binary, il écrira \r\r\n car sous Windows text, chaque \n sera traduit en \r\n.

Dans Python 3, la syntaxe requise a été modifiée. Vous devez donc ouvrir outfile avec le paramètre supplémentaire newline='' à la place.

Exemples:

# Python 2
with open('/pythonwork/thefile_subset11.csv', 'wb') as outfile:
    writer = csv.writer(outfile)

# Python 3
with open('/pythonwork/thefile_subset11.csv', 'w', newline='') as outfile:
    writer = csv.writer(outfile)

Liens de documentation

581
Mark Tolonen

L’ouverture du fichier en mode binaire "wb" ne fonctionnera pas en Python 3+. Ou plutôt, vous devrez convertir vos données en binaire avant de les écrire. C'est juste un problème.

Au lieu de cela, vous devriez le garder en mode texte, mais remplacer le caractère de début de ligne comme étant vide. Ainsi:

with open('/pythonwork/thefile_subset11.csv', 'w', newline='') as outfile:
39
David Maddox

La réponse simple est que les fichiers csv doivent toujours être ouverts en mode binaire que ce soit pour l’entrée ou la sortie, car sinon, Windows posait des problèmes de fin de ligne. Spécifiquement en sortie, le module csv écrira \r\n (le terminateur de ligne standard CSV), puis (en mode texte) le moteur d'exécution remplacera le \n par \r\n (le terminateur de ligne standard Windows) donnant un résultat de \r\r\n.

Jouer avec la lineterminator n'est PAS la solution.

13
John Machin

Remarque: il semble que ce ne soit pas la solution préférée en raison de l'ajout de la ligne supplémentaire sur un système Windows. Comme indiqué dans le document python :

Si csvfile est un objet de fichier, il doit être ouvert avec le drapeau «b» sur les plates-formes où cela fait une différence.

Windows est l'une de ces plateformes où cela fait la différence. Le fait de changer le terminateur de ligne comme je le décris ci-dessous peut avoir résolu le problème, mais le problème pourrait être totalement évité en ouvrant le fichier en mode binaire. On pourrait dire que cette solution est plus "élégante". "Fiddling" avec le terminateur de ligne aurait probablement entraîné un code non transférable entre systèmes, dans ce cas, l'ouverture d'un fichier en mode binaire sur un système unix ne produisant aucun effet. c'est à dire. il en résulte un code compatible entre systèmes.

De (Python Docs }: 

Sous Windows, "b" a été ajouté au mode ouvre le fichier en mode binaire, donc il y a aussi des modes comme 'rb', 'wb', et 'r + b'. Python sous Windows crée un distinction entre texte et binaire des dossiers; les caractères de fin de ligne dans les fichiers texte sont automatiquement modifiés légèrement lorsque les données sont lues ou écrites . Cette modification en coulisse de les données de fichier conviennent pour le texte ASCII fichiers binaires, mais les données binaires corrompues comme ça dans les fichiers JPEG ou EXE. Être très prudent d'utiliser le mode binaire quand lire et écrire de tels fichiers. Sur Unix, ça ne fait pas de mal d’ajouter un 'b' au mode, de sorte que vous pouvez l'utiliser plate-forme indépendante pour tout binaire des dossiers.

Original:

En tant que partie des paramètres facultatifs de csv.writer, si vous obtenez des lignes vides supplémentaires, vous devrez peut-être modifier le marqueur de ligne (info ici ). Exemple ci-dessous, adapté de la page python csv docs. Changez-le de '\ n' à ce que vous devriez être. Comme il ne s'agit que d'un coup de poing dans le noir, cela peut ou non fonctionner, mais c'est ma meilleure hypothèse.

>>> import csv
>>> spamWriter = csv.writer(open('eggs.csv', 'w'), lineterminator='\n')
>>> spamWriter.writerow(['Spam'] * 5 + ['Baked Beans'])
>>> spamWriter.writerow(['Spam', 'Lovely Spam', 'Wonderful Spam'])
6
Derek Litz

Utilisez la méthode définie ci-dessous pour écrire des données dans le fichier CSV.

open('outputFile.csv', 'a',newline='')

Ajoutez simplement un paramètre newline='' supplémentaire dans la méthode open:

def writePhoneSpecsToCSV():
    rowData=["field1", "field2"]
    with open('outputFile.csv', 'a',newline='') as csv_file:
        writer = csv.writer(csv_file)
        writer.writerow(rowData)

Cela écrira des lignes CSV sans créer de lignes supplémentaires!

0
Febin Mathew
with open(destPath+'\\'+csvXML, 'a+') as csvFile:
    writer = csv.writer(csvFile, delimiter=';', lineterminator='\r')
    writer.writerows(xmlList)

Le "lineterminator = '\ r'" permet de passer à la ligne suivante, sans ligne vide entre deux.

0
SheRa

Lorsque vous utilisez Python 3, vous pouvez éviter les lignes vides en utilisant le module codecs . Comme indiqué dans la documentation, les fichiers sont ouverts en mode binaire, aucune modification du kwarg newline n'est donc nécessaire. Je rencontrais le même problème récemment et cela a fonctionné pour moi:

with codecs.open( csv_file,  mode='w', encoding='utf-8') as out_csv:
     csv_out_file = csv.DictWriter(out_csv)
0
JBa