marja
Goto Top

CSV Datei neu anordnen, leere Spalten hinzufügen

Mit Batch kenne ich mich einigermaßen aus, ich hoffe ihr könnt mir bei folgender Frage helfen.

Mit einer Batch Datei möchte ich gerne eine CSV Datei überarbeiten.

Bsp. Original-Datei
Spalte 10; Spalte 2; Spalte 3; Spalte 4; Spalte 9; Spalte 5 ...

Nun möchte ich gerne die Spalten entsprechend ordnen, d.h. das die erste Spalte (wo auch immer sie in der CSV Datei steht) in der neuen CSV Datei am Anfang steht.
Zusätzlich muß ich aber bsp. zwischen Spalte 2 und Spalte 3 eine neue leere Spalte einfügen.

Bsp. Neue-Datei
Spalte 1; Spalte 2; Spalte 3 (neue Spalte), Spalte 4 (alt Spalte 3) usw.

Ich hoffe ihr könnt mir helfen.

LG Marja

Content-Key: 166800

Url: https://administrator.de/contentid/166800

Ausgedruckt am: 29.03.2024 um 02:03 Uhr

Mitglied: bastla
bastla 24.05.2011 um 12:43:32 Uhr
Goto Top
Hallo Marja!
die erste Spalte (wo auch immer sie in der CSV Datei steht)
... wäre woran zu erkennen, bzw
  • Nach welchem Kriterium soll sortiert werden?
  • Wie viele Spalten gibt es?
  • Ist das Leerzeichen am Beginn jeder Spalte Absicht?
und
  • Gibt es einen Einwand gegen die (zumindest temporäre) Verwendung von VBS?

Grüße
bastla
Mitglied: Marja
Marja 24.05.2011 um 13:16:24 Uhr
Goto Top
Hallo Bastla

sorry, da habe ich mich falsch ausgedrückt. Ich hatte die Hilfeanfrage als unviversell angesehen.

Die Original-Datei sieht bsp. wie folgt aus:
Datum;IMEI;Hersteller;Kundenummer;ArtikelNr;ID;Fehler

Diese soll dann bsp. wie folgt aussehen:
ID;Datum;Kundenummer;KontaktNr;ArtikelNr;Hersteller;Ansprechpartner;Fehler;

KontaktNr und Ansprechpartner sind neu hinzugekommen.
Alles andere wurde neu angeordnet. Die Datei muß als CSV in einem anderen Programm weiter aufbereitet werden.

Das Leerzeichen war keine Absicht, ich dachte nur das man dadurch das Simikolon besser sieht.

Ich habe schon einiges probiert. Was mich interessiert wie sage ich das bsp. Spalte 10 an Platz 1 kommt, Spalte 7 an Platz 2 und so weiter.
Außerdem wie bsp. an Platz 3 dann eine neue Spalte angelegt wird ohne Inhalt wenn möglich?

LG Marja
Mitglied: Lochkartenstanzer
Lochkartenstanzer 24.05.2011 um 13:40:46 Uhr
Goto Top
Zitat von @Marja:
Mit einer Batch Datei möchte ich gerne eine CSV Datei überarbeiten.

Bsp. Original-Datei
Spalte 10; Spalte 2; Spalte 3; Spalte 4; Spalte 9; Spalte 5 ...


Diese drei Zeilen sollten es tun:

cat exceldatei.csc | gawk -F ";" ' { print $20 " ; " $2 " ; <leerzeichen> ; " $3 " ; "$4 " ; " $9 " ; "$5 " ; " ... } >neue-exceldatei.csv
grep "Spaltenbezeichner" neue-exeldatei.csv >sortierte-neue-exceldatei.csv
grep -v "Spaltenbezeichner" neue-exeldatei.csv | sort >>sortierte-neue-exceldatei.csv

gruß

lks

PS. Die Befehle stehen mit cygwin (http://cygwin.com) ) auch unter Windows zur Verfügung.
Mitglied: Lochkartenstanzer
Lochkartenstanzer 24.05.2011 um 13:44:34 Uhr
Goto Top
Zitat von @Lochkartenstanzer:
> Zitat von @Marja:
> ----
> Mit einer Batch Datei möchte ich gerne eine CSV Datei überarbeiten.
>
> Bsp. Original-Datei
> Spalte 10; Spalte 2; Spalte 3; Spalte 4; Spalte 9; Spalte 5 ...
>

Diese drei Zeilen sollten es tun:

cat exceldatei.csc | gawk -F ";" ' { print $20 " ; " $2 " ; <leerzeichen> ; " $3
" ; "$4 " ; " $9 " ; "$5 " ; " ... } >neue-exceldatei.csv
grep "Spaltenbezeichner" neue-exeldatei.csv >sortierte-neue-exceldatei.csv

Hier noch ein

sed -e "s/Kundenummer; ;ArtikelNr/Kundenummer;KontaktNr;ArtikelNr/g" -i sortierte-neue-exceldatei.csv

eingefügt und schon hast Du die Header auch angepaßt. face-wink

grep -v "Spaltenbezeichner" neue-exeldatei.csv | sort >>sortierte-neue-exceldatei.csv

gruß

lks

PS. Die Befehle stehen mit cygwin (http://cygwin.com) ) auch unter Windows zur Verfügung.

Mitglied: bastla
bastla 24.05.2011 um 13:47:50 Uhr
Goto Top
Hallo Marja!

Ich würde, wie schon erwähnt, VBS verwenden:
Alt = "D:\Die.csv"  
Neu = "D:\Die neue.csv"  
Delim = ";"  

Set fso = CreateObject("Scripting.FileSystemObject")  
Zeilen = Split(fso.OpenTextFile(Alt).ReadAll, vbCrLf)
Set DateiNeu = fso.CreateTextFile(Neu)
For Each Zeile In Zeilen
    If Trim(Zeile) = "" Then 'Leerzeile oder nur Leerzeichen enthalten  
        ZeileNeu = Zeile
    Else
        Felder = Split(Zeile, Delim) 'anhand des Trennzeichens <Delim> in Felder zerlegen  
        ZeileNeu = _
            Felder(5) & Delim & _
            Felder(0) & Delim & _
            Felder(3) & Delim & _
            Delim & _
            Felder(4) & Delim & _
            Felder(2) & Delim & _
            Delim & _
            Felder(6)
    End If	
    DateiNeu.WriteLine ZeileNeu
Next
Zu beachten: Die Feldnummern beginnen bei 0 ...

Grüße
bastla
Mitglied: Friemler
Friemler 24.05.2011 um 13:51:03 Uhr
Goto Top
Hallo Marja,

hier mal ein Vorschlag als Batchscript:
@echo off

setlocal


set "InputFile=Test.csv"  
set "OutputFile=Out.csv"  


::Altes Spaltenlayout
::Datum;IMEI;Hersteller;Kundenummer;ArtikelNr;Id;Fehler

::Neues Spaltenlayout
::Id;Datum;Kundenummer;KontaktNr;ArtikelNr;Hersteller;IMEI;Ansprechpartner;Fehler

set "ColLayout=6 1 4 5 3 2 7"  
set "NewColumns=4 7"  
set "NewColumnsHeader=Kontaktnummer Ansprechpartner"  

type NUL > "%OutputFile%"  


set /a MaxCol=0

for %%i in (%ColLayout%) do (
  call :GetMaxCol %%i
)


set /a RowCount=1

for /f "usebackq eol= delims=" %%l in ("%InputFile%") do (  
  set "Line=%%l"  
  call :ProcessLine
)

exit /b



:ProcessLine
set /a ColCount=0

for %%i in (%ColLayout%) do (
  set /a ColCount+=1
  call :WriteNewColumn
  call :WriteColumn %%i
)

>>"%OutputFile%" echo.  
set /a RowCount+=1
exit /b



:WriteNewColumn
set /a Idx=1

for %%j in (%NewColumns%) do (
  if "%%j" equ "%ColCount%" (  
    if %RowCount% equ 1 (
      call :WriteNewColumnHeader
    ) else (
      >>"%OutputFile%" <NUL set /p "=;"  
    )
  )

  set /a Idx+=1
)

exit /b



:WriteNewColumnHeader
for /f "tokens=%Idx%" %%k in ("%NewColumnsHeader%") do (  
  >>"%OutputFile%" <NUL set /p "=%%k;"  
)

exit /b



:WriteColumn
for /f "tokens=%1 eol= delims=;" %%c in ("%Line%") do (  
  if %ColCount% lss %MaxCol% (
    >>"%OutputFile%" <NUL set /p "=%%c;"  
  ) else (
    >>"%OutputFile%" <NUL set /p "=%%c"  
  )
)

exit /b



:GetMaxCol
if %1 gtr %MaxCol% set /a MaxCol=%1
exit /b

Einschränkung:
In der Quelldatei dürfen höchstens 31 Spalten vorkommen.

Erklärung:
In Zeile 16 wird das Spaltenlayout festgelegt. Das Beispiel bedeutet:
  • Die erste Spalte der Quelldatei ist auch die erste Spalte in der Zieldatei (1 steht auf dem ersten Platz der Liste)
  • Die vierte Spalte der Quelldatei wird zur zweiten Spalte der Zieldatei (4 steht auf dem zweiten Platz der Liste)
  • Die zweite Spalte der Quelldatei wird zur dritten Spalte der Zieldatei (2 steht auf dem dritten Platz der Liste)
  • usw.

In Zeile 17 werden die Nummern der Spalten festgelegt , vor denen eine neue Spalte eingefügt werden soll. Die Zählung bezieht sich auf die Spaltennummern in der Zieldatei, ohne die neu hinzugefügten Spalten mitzuzählen . Die Nummern müssen in aufsteigender Reihenfolge angegeben werden.

In Zeile 18 werden die Header der neuen Spalten festgelegt. Die Reihenfolge muss mit der der Nummern der neuen Spalten aus Zeile 17 korrespondieren.

Bei weiteren Fragen zur Funktionsweise, lass hören.

Gruß
Friemler
Mitglied: Marja
Marja 24.05.2011 um 13:51:38 Uhr
Goto Top
erst einmal vielen Dank.

Er kann mit cat nichts anfangen.

Sonst verstehe ich aber den Code so, das Du in der ersten Zeile die Sortierung durchführst.
Mit Grep kann ich so nichts anfangen und in der sed Zeile wird der Header (Kopf) bearbeitet.

LG Marja
Mitglied: Friemler
Friemler 24.05.2011 um 14:00:25 Uhr
Goto Top
Hallo marja,

cat, grep und sed sind Befehle aus der UNIX-Welt, die auf einem Windows-System nicht vorhanden sind. Deshalb der Link auf Cygwin. Das musst Du zuerst installieren, um spezielle Portierungen von UNIX-Befehlen, die Cygwin benötigen, ausführen zu können.

Gruß
Friemler
Mitglied: Lochkartenstanzer
Lochkartenstanzer 24.05.2011 um 14:04:46 Uhr
Goto Top
Hier die Erläuterungen dazu


cat exceldatei.csc | gawk -F ";" ' { print $20 " ; " $2 " ; <leerzeichen> ; " $3 " ; "$4 " ; " $9 " ; "$5 " ; " ... } >neue-exceldatei.csv

cat gibt die exceldatei aus und diese wird durch den Befehl gawk verarbeitet, in dem einzelne Elemente in anderer Reihenfolge ausgegeben werden. Das Ergebnis wird in die neue-exceldatei.csv geschrieben.

grep "Spaltenbezeichner" neue-exeldatei.csv >sortierte-neue-exceldatei.csv

Damit schreibe ich die Spaltenüberschriften als erste zeile in die sortierte-neue-exceldatei.csv

sed -e "s/Kundenummer; ;ArtikelNr/Kundenummer;KontaktNr;ArtikelNr/g" -i sortierte-neue-exceldatei.csv

Hier wird in der Spaltenüberschrift noch die Kontaktnummer hineingeschrieben.

grep -v "Spaltenbezeichner" neue-exeldatei.csv | sort >>sortierte-neue-exceldatei.csv

grep verabeitet die neue-Exceldatei und verwirft die Zeile mit den Spaltenbezeichnern (wurde ja schon geschrieben) und das wird durch sort durchsortiert. ggf. muß man hier durch parameter noch angeben, nach welchem Feld sortiert werden soll. Das Ergebnis landet dann in sortierte-neue-exceldatei.csv hinter den SPaltenbezeichnern.

Die Befehle cat, gawk, sed, grep und sort sind Standardbefehle unter unixoiden Systemen und stehen mit http://www.cygwin.com auch unter windows zur Verfügung.
Mitglied: Marja
Marja 24.05.2011 um 14:14:15 Uhr
Goto Top
o.k. verstehe. mit Windows befehlen ist dies nicht möglich?

Hintergrund: Ich darf hier leider nichts auf dem Firmen PC installieren, die Batch Datei wird später an verschiedenen Clients eingesetzt und da ist installieren definitiv nicht möglich/erlaubt.

Hmmm, ich schau mir aber mal den Link an.

Danke für eure Hilfe.

LG Marja
Mitglied: Friemler
Friemler 24.05.2011 um 14:19:56 Uhr
Goto Top
Hallo Marja,

Zitat von @Marja:
mit Windows befehlen ist dies nicht möglich?

das hört man aber garnicht gerne face-wink .

Ausserdem: Oben stehen zwei Lösungen (VBS und Batch), das sind Windows-Bordmittel.

Gruß
Friemler
Mitglied: Lochkartenstanzer
Lochkartenstanzer 24.05.2011 um 14:30:40 Uhr
Goto Top
Zitat von @Marja:
o.k. verstehe. mit Windows befehlen ist dies nicht möglich?

Doch! s.o. Sieht halt nur nicht ganz so elegant aus.


Hintergrund: Ich darf hier leider nichts auf dem Firmen PC installieren, die Batch Datei wird später an verschiedenen Clients
eingesetzt und da ist installieren definitiv nicht möglich/erlaubt.

Da ist die Frage, ob für solch einen Einsatzzweck die Admins keine Ausnahme machen. Einfach mal fragen. Die entsprechenden Tools kamm nan übrigens auch ohne explizite Installation des Gesamtpakets verwenden. Man muß sich dann halt nur die einzelnen Befehle und die cygwin..dll heraussuchen und in ein User-Verzeichnis packen.


Hmmm, ich schau mir aber mal den Link an.

Danke für eure Hilfe.

LG Marja

gern geschehen.

lks
Mitglied: Marja
Marja 24.05.2011 um 15:09:35 Uhr
Goto Top
das sieht super aus, super vielen lieben dank für eure Hilfe.

Ich schau mir das gleich morgen früh an, muss jetzt leider los.

Vielen Dank nochmal.

LG Marja
Mitglied: Biber
Biber 24.05.2011 um 18:00:11 Uhr
Goto Top
Moin Lochkartenstanzer,

Zitat von @Lochkartenstanzer:
Da ist die Frage, ob für solch einen Einsatzzweck die Admins keine Ausnahme machen. Einfach mal fragen.
Ich kann da ja nicht für andere Admins sprechen.
Aber: Wenn bei mir jemand anklopfen würde, der cygwin installieren wollte, weil eine Import/Export-CSV-Datei umsortiert werden muss, weil irgendwer es nicht auf die Reihe bekommen hat, nun gleich alle vielen beiden zwei Seiten einer Schnittstelle zeitgleich aktiv zu setzen...

Hey - es gibt in diesem Szenario nur zwei mögliche Varianten.
Entweder die Jungs & Mädels bringen glaubhaft dar, dass dieses Zwangs-Kompatibel-Pressen halt wegen diesen und jenen Softwareproblemen befristet für ein oder zwei Wochen sein muss.
Dann-> Hey, für eine befristete Übergangsfrickelei gibt es keine Ausnahmeinstallation, wenn es auch mit Bordmitteln geht.
Was soll die Ästhetik und Eleganz, wenn dieser Bypass ohnehin in zwei Wochen Asche ist.

-oder-
Die Jungs & Mädels sagen, die wollen dieses Gewurschtel dauerhaft als Teil einer produktiven Prozesskette betreiben.
Dann -> will ich eine Kopie der "produktiv eingesetzten" Skriptversion mit Beschreibung, Tel-Nummer der Autors und das ganze Skript dokumentiert. Auch wenn es bedeutet, dass für eine sed-Halbzeile eine DIN-A4-Seite Doku getippt wird.

Und das Skriptchen wird, wenn irgendwie möglich, event- oder zeitgesteuert gestartet und ist ohne Adminrechte bestenfalls lesbar etc pp.
Denn wenn es als Teil der betrieblichen Prozesse unabdingbar ist, dann gelten auch die Regeln für produktiv eingesetzte Programme.
In diesem Fall würde ich cygwin oder was-auch-immer installieren.

Frage ist nur, ob denn irgendein Hierarch tatsächlich diese Bankrotterklärung ("Wir bekommen die Schnittstelle zur Lohnbuchhaltung nur mit Gefrickel hin") unterschreiben wird.

Das darf doch bei Export/Importschnittstellen wohl nicht wahr sein, dass die Änderung der Spaltenanzahl- oder Reihenfolge im erzeugenden oder lesenden Programm so furchtbar zeitaufwändig ist.

Grüße
Biber
Mitglied: Lochkartenstanzer
Lochkartenstanzer 24.05.2011 um 21:35:07 Uhr
Goto Top
Zitat von @Biber:
Moin Lochkartenstanzer,

> Zitat von @Lochkartenstanzer:
> ----
> Da ist die Frage, ob für solch einen Einsatzzweck die Admins keine Ausnahme machen. Einfach mal fragen.
Ich kann da ja nicht für andere Admins sprechen.

Vielleicht sorgt ja die Frage bei den Admins dafür, daß die Schnittstelle klargezogen wird. face-smile

Sofern diese Konvertierung duaerhaft beötigt wird, wäre meine Vorgehensweise, den Zuständigen für die beiden System auf die Füße zu treten, daß die ein kompatibles Austauschformat festlegen.

Ist es nur kurtfristig, würde ich mir eine Station als Konverter ausgucken, auf der zwei Freigaben einrichten (z.B. In und Out) und per skript alles was in "in" bgelegt wird konvertiert auf "out" ablegen. Sofern dann die System Dateien speichern /einlesen die Daten austauschen, wäre damit das Problem gelöst. (vermutlich ist es dann ein Provisorium für die Ewigkeit.)

Daß auch für Einzeiler eine Dokumentation dazugehört ist natürlich selbtverstädnlich.

lks
Mitglied: Marja
Marja 25.05.2011 um 08:21:18 Uhr
Goto Top
Nochmals vielen Dank.

Leider funktioniert das nicht wirklich zu 100%. Zu einem macht er den Header korrekt, aber dann fügt er nicht mehr richtig die Spalten ein.
Habe es sogar einzeln probiert um zu prüfen wo er nun die neue Spalte einfügt.

Zum anderen, macht er zwar den Header fast richtig, aber die zugehörigen Daten in den Spalten haut er daneben, warum auch immer ;-(

Habe parallel die Script von Bastla probiert. Der funktioniert. Leider weiß ich nicht, wie ich den Header überarbeiten kann.


LG Marja
Mitglied: Marja
Marja 25.05.2011 um 08:22:43 Uhr
Goto Top
oh sorry face-wink))

Ja, die Lösung habe ich dann gesehen, war ein wenig verwirrt mit den Antworten im Thread face-wink
Nun habe ich alles gefunden.

LG Marja
Mitglied: bastla
bastla 25.05.2011 um 09:20:31 Uhr
Goto Top
Hallo Marja!

Der Vollständigkeit halber die passende VBS-Variante (ungetestet):
Alt = "D:\Die.csv"  
Neu = "D:\Die neue.csv"  
Delim = ";"  
'Falls der Header aus der Datei übernommen werden soll, als nächste Zeile: Header = ""  
Header = "ID;Datum;Kundenummer;KontaktNr;ArtikelNr;Hersteller;Ansprechpartner;Fehler"  

Set fso = CreateObject("Scripting.FileSystemObject")  
Zeilen = Split(fso.OpenTextFile(Alt).ReadAll, vbCrLf)
Set DateiNeu = fso.CreateTextFile(Neu)
If Header <> "" Then  
    DateiNeu.WriteLine Header
    Ab = 1
End If
For i = Ab To UBound(Zeilen)
    If Trim(Zeilen(i)) = "" Then 'Leerzeile oder nur Leerzeichen enthalten  
        ZeileNeu = Zeilen(i)
    Else
        Felder = Split(Zeilen(i), Delim) 'anhand des Trennzeichens <Delim> in Felder zerlegen  
        ZeileNeu = _
            Felder(5) & Delim & _
            Felder(0) & Delim & _
            Felder(3) & Delim & _
            Delim & _
            Felder(4) & Delim & _
            Felder(2) & Delim & _
            Delim & _
            Felder(6)
    End If	
    DateiNeu.WriteLine ZeileNeu
Next
Da Du ja ohnehin "Hand anlegen" musst, kannst Du die Headerzeile auch gleich komplett selbst erstellen und dann beim Auslesen die Zeile 1 der CSV-Datei überspringen ...

Grüße
bastla
Mitglied: Marja
Marja 25.05.2011 um 10:00:56 Uhr
Goto Top
Hallo Bastla,

der Code funktioniert. Super.

Wie kann ich ggf. noch den Headernamen überarbeiten?

LG Marja
Mitglied: bastla
bastla 25.05.2011, aktualisiert am 18.10.2012 um 18:46:59 Uhr
Goto Top
Hallo Marja!

Ist wirklich unübersichtlich hier ... face-wink

Der geänderte Ansatz steht schon da unten.

Grüße
bastla
Mitglied: Marja
Marja 25.05.2011 um 10:32:38 Uhr
Goto Top
Danke Dir.

Es scheint super zu funktionieren, hatte irgendwo einen Fehler drin, den ich aber gefunden habe.
Das einzigste was er nun macht ist, wenn ich die Datei in Excel öffne, das er mir sagt "Kann Datensatz 1 nicht lesen. Weiterhin jeden Fehler anzeigen?"

Hmmm, das war vorher nicht. Woran kann das liegen?

Die zweite Meldung ist, das Excel festgestellt hat, das die Datei eine SYLK-Datei ist, aber es kann die Datei nicht laden. Entweder ist die Datei fehlerhaft oder ein ungültiges SYLK-Dateiformat. Nach Klick auf OK sehe ich aber die Daten.

LG Marja
Mitglied: bastla
bastla 25.05.2011 um 10:36:42 Uhr
Goto Top
Hallo Marja!
hatte irgendwo einen Fehler drin, den ich aber gefunden habe.
Kann bei ungetesteten Scripts leider passieren - ich würde ihn gerne oben im Code noch korrigieren ...
Die zweite Meldung ist, das Excel festgestellt hat, das die Datei eine SYLK-Datei ist, aber es kann die Datei nicht laden.
http://support.microsoft.com/kb/215591/de

Grüße
bastla
Mitglied: Marja
Marja 25.05.2011 um 12:24:50 Uhr
Goto Top
alles klar, danke Dir.

Der ungetestete Code war korrekt, habe ihn falsch abgeschrieben vermutlich, da er mich immer auf die Zeile 22 verwies.
Es hatte irgendwas mit dem ersten Feld auslesen zu tun gehabt.

Dann habe ich den Code kopiert und eingefügt und es funktioniert.
Habe zwar keinen unterschied zu meinem manuell eingegebenen Code gesehen, aber es funktioniert face-wink

Habe mich blöd ausgedrückt. Also alles o.k. mit Deinem ungetesteten Code face-wink)

Marja
Mitglied: Friemler
Friemler 25.05.2011 um 13:56:17 Uhr
Goto Top
Hallo Marja,

Zitat von @Marja:
Dann habe ich den Code kopiert und eingefügt und es funktioniert.

ich schätze mal, das würde mit meinem Batchscript auch so sein, bei mir funktioniert es nämlich.

Ich habe übrigens noch die Ergänzung der Headerzeile eingebaut.

Gruß
Friemler
Mitglied: Biber
Biber 25.05.2011 um 19:36:10 Uhr
Goto Top
[OT] @bastla

Moin bastla,
Zitat von @bastla:
> Die zweite Meldung ist, das Excel festgestellt hat, das die Datei eine SYLK-Datei ist, aber es kann die Datei nicht laden.
http://support.microsoft.com/kb/215591/de
Vielen, vielen Dank für diesen Link.
Ich habe mich beinahe eingenässt zunehmend amüsiert beim Lesen.
"Auf ProgrammierpraktikantInnen ist Verlass" dachte ich an dieser Stelle:
Das Problem tritt auf, wenn Sie eine Textdatei öffnen und die ersten beiden Zeichen der Datei die Großbuchstaben ID sind
Auf so blöde Ideen kommt wirklich nicht jeder Coder.
Und bei der 5-Punkte-Anleitung "Wie gebe ich einen Apostroph ein?", da dachte ich nur: "Das sichere ich mir als PDF-Datei."

Grüße
Biber
[/OT]