2011-03-29 2 views
10

J'utilise PHP pour importer un fichier CSV provenant d'une feuille de calcul Excel. Certains des champs contiennent des sauts de ligne, donc quand je rouvre le fichier csv dans une feuille de calcul Excel/Open Office, il interprète mal où les sauts de ligne devraient se produire.Importation de fichiers CSV comportant des sauts de ligne dans les champs réels

Également dans mon script, en utilisant fgetcsv pour parcourir chaque ligne, il est incorrect de couper la ligne là où il ne devrait pas l'être.

je pouvais nettoyer manuellement les données, mais a) cela prendrait âges que son fichier de ligne 10k, et b) les données sont exportées à partir d'un des clients existants logiciel

Toutes les idées sur la façon de résoudre automatiquement ce sur le processus d'importation? J'aurais pensé que délimiter les champs l'aurait trié mais ce n'est pas le cas.

+1

tant les champs avec des sauts de ligne sont indiqués ' « foo \ nbar »' les alignements de colonnes ne doivent pas être affectés – xzyfer

+1

LF doit être codé comme '\ n' dans les champs CSV. Vous aurez besoin d'un lecteur personnalisé pour annuler les dommages d'exportation. Regardez à travers http://php.net/fgetcsv, mais vous devrez probablement chercher ou en écrire un. – mario

+2

double possible (http://stackoverflow.com/questions/3278375/how-can-you-parse-excel-csv-data-that-contains-linebreaks-in-the-data) – xzyfer

Répondre

3

J'ai eu ce problème aussi et je n'ai pas trouvé un moyen de lire correctement les données. Dans mon cas c'était une importation unique, donc j'ai fait un script qui a cherché toutes les sauts de ligne dans une colonne et l'a remplacé par quelque chose comme #####. Puis j'ai importé les données et les ai remplacées par des sauts de ligne.

Si vous avez besoin d'une importation régulière, vous pouvez écrire votre propre CSV-Parser, qui gère le problème. Si les colonnes de texte sont dans "" vous pouvez traiter tout entre deux "" comme une colonne (avec la vérification de " échappé dans le contenu).

+0

Pourriez-vous partager le code ou la regex que vous avez utilisé? cela? – Zahymaka

0

Oui, vous devez trouver cette virgule et remplacer par des caractères spéciaux comme la combinaison de {()} et enfin les remplacer par , que vous recherchez à l'origine.

Espérons que cela vous aide.

+3

désolé mais cela ne suffit pas du tout, s'il vous plaît lire effectivement toute la question avant de répondre à – Horse

11

La réponse acceptée n'a pas résolu le problème pour moi, mais j'ai finalement trouvé cette bibliothèque d'analyseur CSV sur google code qui fonctionne bien pour les champs multilignes dans CSV.

parsecsv-pour-php: http://code.google.com/p/parsecsv-for-php/

+0

merci pour le partage :) – simon

+0

+1 C'est jusqu'à présent le meilleur analyseur autour! mieux que str_getcsv ou similaire. Mes données contenaient du HTML et de nouvelles lignes dans les champs. C'est le seul analyseur qui a eu raison! Merci! – lepe

+1

Il est un peu triste qu'il soit si difficile de trouver un analyseur précis pour l'un des formats les plus courants pour l'un des langages de programmation les plus utilisés. Je suppose que c'est partiellement parce qu'il n'y a pas de norme officielle, mais les sauts de ligne à l'intérieur des valeurs entre guillemets sont certainement quelque chose qu'un analyseur CSV devrait être capable de gérer. – danieltalsky

1

Ma solution est la suivante: niveau

nl2br(string); 

http://php.net/manual/en/function.nl2br.php

Une fois que vous obtenez à la cellule individuelle (string), exécutez-le chaîne et il convertira les sauts de ligne en pauses html pour vous.

0

Bien que ce soit une vieille question, la réponse pourrait être toujours pertinente pour ppl. Il existe actuellement une nouvelle bibliothèque (indépendante du framework) http://csv.thephpleague.com/ qui prend en charge les caractères NL dans les champs ainsi qu'un certain filtrage.

0

C'est un ancien thread mais j'ai rencontré ce problème et je l'ai résolu avec une regex afin que vous puissiez éviter une bibliothèque juste pour cela. Ici, le code est en PHP mais il peut être adapté à d'autres langues.

$parsedCSV = preg_replace('/(,|\n|^)"(?:([^\n"]*)\n([^\n"]*))*"/', '$1"$2 $3"', $parsedCSV);

Cette solution suppose les champs contenant un saut de ligne sont entourés par des guillemets doubles, ce qui semble être une hypothèse valable, au moins pour ce que je l'ai vu jusqu'à présent.En outre, les guillemets doivent suivre un , ou être placés au début d'une nouvelle ligne (ou première ligne).

Exemple:

field1,"field2-part1\nfield2-part2",field3

Ici, le \ n est remplacé par un espace de sorte que le résultat serait:

field1,"field2-part1 field2-part2",field3

Le regex doit gérer plusieurs sauts de ligne aussi bien.

Ceci peut ne pas être efficace si le contenu est trop grand, mais cela peut aider dans de nombreux cas et l'idée peut être réutilisée, peut-être optimisée en faisant cela pour des morceaux plus petits (mais vous devrez gérer les coupes avec correction -size tamponné).

Questions connexes