zwei csv-Dateien zusammen fügen

31/05/2008 - 21:24 von aegeling | Report spam
Hallo Community!

Ich soll fortan regelmàßig Daten aus einer Datenbank in die einer anderen
einpflegen. Beides sind Mitgliedsdatenbanken und beinhalten Personendaten.
Diese Daten liegen mir aus beiden Datenbanken als .csv-Dateien vor. Problem
ist, dass sie aus zwei unterschiedlichen Datenbanken stammen und daher nicht
die gleichen Spalten haben und auch nicht in der gleichen Art und Weise
gespeichert werden. Damit das anschaulicher wird, hier mal Auszüge aus den
Original-csv-Dateien, allerdings verfremdet:


Datei1.csv:
"mitgliedsnr";"name";"geburtsname";"vorname";"titel";"strasse";"hausnr"
"100000";"Müller";"Meier";"Anglika";"Dr.";"Vogelweg";"24 c"
"100001";"Schulze";"";"Hubert";"Dr.";"Sàugetierstr.";"26"

Datei2.csv:
STAMMNUMMER;NAME;TITEL;VORNAME;GEBURTSDATUM;STRASSE
100001;Schulze;;Hubert;01.01.1900;Sàugetierstr. 26
100002;Richter;;Alexander;01.01.1979;Reptilweg 7


Die Daten aus „Datei1.csv“ sollen in „Datei2.csv“ eingelesen werden,
allerdings nur die Spalten „Mitgliedsnummer“/“Stammnummer“,
„Nachname“/„Name“, „Vorname“.

Nun könnte ich einfach beide Tabellen in Excel öffnen und die gewünschten
Inhalte aus Datei1 ans Ende von Datei2 kopieren. Dabei gibt es aber mehrere
Probleme:
1. Gibt es viele redundante Daten. Die, die schon in Datei2 vorliegen
sollten also am besten gar nicht erst aus Datei1 kopiert werden.
2. Wenn das erste Problem gelöst ist und alle Daten in einer Datei
vorliegen, muss diese wieder als csv gespeichert werden und zwar mit genau
den Separatoren, die auch vorher schon genutzt wurden. In Datei2 wàre das
also ein Semikolon, wobei zu beachten ist, dass die einzelnen Zellinhalte
nicht durch Anführungszeichen umgeben sein sollen (wie dies in Datei1 der
Fall ist).
Eine mögliche Lösung dafür habe ich glaube ich schon mal hier gefunden:
http://www.vb-fun.de/cgi-bin/forumarchiv.pl?archiv04&ID=1&action=zeigeseite&nummer0014#Atext
Allerdings kenne ich mich gar nicht mit VBA aus und kann daher auch nicht
sagen, ob das hilft oder wie ich es „einbauen“ müsste.

Mit besten Grüßen,
aegeling
 

Lesen sie die antworten

#1 Reiner Wolff
01/06/2008 - 11:56 | Warnen spam
Moin Aegeling,

hier ist es üblich, seinen Vor- und Zunamen anzugeben.
Ich hoffe, ich habe Dich trotzdem richtig angesprochen :-)

*aegeling* schrieb:
Ich soll fortan regelmàßig Daten aus einer Datenbank in die einer anderen
einpflegen. Beides sind Mitgliedsdatenbanken und beinhalten Personendaten.
Diese Daten liegen mir aus beiden Datenbanken als .csv-Dateien vor. Problem
ist, dass sie aus zwei unterschiedlichen Datenbanken stammen und daher nicht
die gleichen Spalten haben und auch nicht in der gleichen Art und Weise
gespeichert werden. Damit das anschaulicher wird, hier mal Auszüge aus den
Original-csv-Dateien, allerdings verfremdet:

Datei1.csv:
"mitgliedsnr";"name";"geburtsname";"vorname";"titel";"strasse";"hausnr"
"100000";"Müller";"Meier";"Anglika";"Dr.";"Vogelweg";"24 c"
"100001";"Schulze";"";"Hubert";"Dr.";"Sàugetierstr.";"26"
Datei2.csv:
STAMMNUMMER;NAME;TITEL;VORNAME;GEBURTSDATUM;STRASSE
100001;Schulze;;Hubert;01.01.1900;Sàugetierstr. 26
100002;Richter;;Alexander;01.01.1979;Reptilweg 7

Die Daten aus ¥Datei1.csvŽ sollen in ¥Datei2.csvŽ eingelesen werden,
allerdings nur die Spalten ¥MitgliedsnummerŽ/ŽStammnummerŽ,
¥NachnameŽ/¥NameŽ, ¥VornameŽ.



Wenn das beides Tabellen in einer Datenbank (MDB-Datei) wàren, könntest Du
die dazu passende SQL-Abfrage formulieren?
In etwa so:
Select MitgliedsNr, Name, Vorname
From Datei1.csv
Union
Select StammNummer, Name, Vorname
From Datei2.csv

Nun könnte ich einfach beide Tabellen in Excel öffnen und die gewünschten
Inhalte aus Datei1 ans Ende von Datei2 kopieren. Dabei gibt es aber mehrere
Probleme:
1. Gibt es viele redundante Daten. Die, die schon in Datei2 vorliegen
sollten also am besten gar nicht erst aus Datei1 kopiert werden.



Das Union Select sollte keine derartigen redundanten Daten enthalten.

2. Wenn das erste Problem gelöst ist und alle Daten in einer Datei
vorliegen, muss diese wieder als csv gespeichert werden und zwar mit genau
den Separatoren, die auch vorher schon genutzt wurden. In Datei2 wàre das
also ein Semikolon, wobei zu beachten ist, dass die einzelnen Zellinhalte
nicht durch Anführungszeichen umgeben sein sollen (wie dies in Datei1 der
Fall ist).



Auch dies könnte man über den ADO-Zugriff auf Textdateien lösen.

Eine mögliche Lösung dafür habe ich glaube ich schon mal hier gefunden:
http://www.vb-fun.de/cgi-bin/forumarchiv.pl?archiv04&ID=1&action=zeigeseite&nummer0014#Atext
Allerdings kenne ich mich gar nicht mit VBA aus und kann daher auch nicht
sagen, ob das hilft oder wie ich es ¥einbauenŽ müsste.



Da hast Du ein Problem, bei dem ich Dir nicht wirklich weiterhelfen kann.
Ich poste Dir trotzdem mal den VBA-Code, den man imo für Dein Problem
anpassen können müsste (ungetestet).

Angepassen wird man ihn aber müssen.
Die Grundidee dabei ist halt, Excel für den Zugriff überhaupt nicht zu
nutzen, sondern über die Jet-Engine auf die CSV-Dateien zuzugreifen.
Für diesen Lösungsansatz benötigst Du allerdings sowohl SQL- als auch
VB(A)-Kenntnisse.

Leider ist mir auf die Schnelle keine Lösung ohne SQL und VBA eingefallen.

HTH
Gruß aus Kiel
Reiner

Code:

Public Sub JoinÜberTextdateien()
'Zeigt am Beispiel einen "Join" über 2 ADODB.Recordsets
Dim cnn1 As ADODB.Connection
Dim cnn2 As ADODB.Connection
Dim cnnTxt As ADODB.Connection
Dim rs1 As ADODB.Recordset
Dim rs2 As ADODB.Recordset
Dim recErgebnis As ADODB.Recordset
Dim str As String
Dim i As Long

'Verbindungen öffnen
'zur 1ten Datenbank
Set cnn1 = New ADODB.Connection
cnn1.ConnectionString = ConnectionStringErmitteln()
cnn1.Open

'zur 2ten Datenbank
Set cnn2 = New ADODB.Connection
cnn2.ConnectionString = ConnectionStringErmitteln()
cnn2.Open

'Zu den Textdateien
Set cnnTxt = New ADODB.Connection
cnnTxt.ConnectionString = "Provider=Microsoft.Jet.OLEDB.4.0;Data Source=c:\;Extended Properties=""text;HDR=Yes;FMT=Delimited"""
cnnTxt.Open

'Recordsets öffnen
Set rs1 = New ADODB.Recordset
rs1.Open "Select * From tblMitarbeiter", cnn1, adOpenForwardOnly, adLockReadOnly

Set rs2 = New ADODB.Recordset
rs2.Open "Select * From tblStandort", cnn2, adOpenForwardOnly, adLockReadOnly

'Recordsets speichern
str = ""
For i = 0 To rs1.Fields.Count - 1
str = str & rs1.Fields(i).Name & ";"
Next '(1) r i = 0 To rs1.Fields.Count - 1
str = str & vbNewLine & rs1.GetString(, , ";", vbNewLine)
WriteFile "C:s1.txt", str

str = ""
For i = 0 To rs2.Fields.Count - 1
str = str & rs2.Fields(i).Name & ";"
Next '(1) r i = 0 To rs2.Fields.Count - 1
str = str & vbNewLine & rs2.GetString(, , ";", vbNewLine)
WriteFile "C:s2.txt", str

'Den Join im Recordset aufrufen
Set recErgebnis = New ADODB.Recordset
recErgebnis.Open "Select Nachname, Vorname, Ortsname From [rs1.txt] As T1 Inner Join [rs2.txt] As T2 On T1.StONr = T2.StONr Where PNr = 000", cnnTxt, adOpenForwardOnly, adLockReadOnly

Cells.ClearContents
Cells(1, 1).CopyFromRecordset recErgebnis
End Sub '(0) TextdateiRecordset()

'folgender Code von www.vb-tec.de entnommen
Sub WriteFile(ByRef Path As String, ByRef Text As String)
Dim FileNr As Long

'Wenn Datei unveràndert, dann abbrechen (ggf. weglassen):
If FileExists(Path) Then _
If FileLen(Path) = Len(Text) Then _
If ReadFile(Path) = Text Then Exit Sub

'Text speichern:
FileNr = FreeFile
Open Path For Output As #FileNr
Print #FileNr, Text;
Close #FileNr
End Sub '(1) f FileExists(Path) Then ...

Public Function FileExists(Path As String) As Boolean
Const NotFile = vbDirectory Or vbVolume

On Error Resume Next
FileExists = (GetAttr(Path) And NotFile) = 0
On Error GoTo 0
End Function '(0) FileExists(Path As String) As Boolean

Function ReadFile(ByRef Path As String) As String
Dim FileNr As Long

'Falls nicht vorhanden, nichts zurückgeben:
On Error Resume Next
If FileLen(Path) = 0 Then Exit Function
On Error GoTo 0

'Datei einlesen:
FileNr = FreeFile
Open Path For Binary As #FileNr
ReadFile = Space$(LOF(FileNr))
Get #FileNr, , ReadFile
Close #FileNr
End Function


Computer sind grossartig. Mit ihnen macht man die Fehler viel schneller.

Ähnliche fragen