Code-Beispiel
CSVLoader
Lizenz: | Erster Autor: | Letzte Bearbeitung: |
FBPSL | chutullu | 05.12.2009 |
CSVLoader - Version 1.
dieses kleine Programm lädt komplette CSV-Datei mit konstanter Spalten bzw. Zeilenanzahl in ein eindimmensionales
StringArray.
Die Adressierung erfolgt über aktuelle Zeile * max Spaltenanzahl + aktuelle Spalte und der Speicher des Arrays
berechnet ganz einfach nach : max. Spaltenzahl * max. Zeilenanzahl .
Es findet keine Dateiprüfung nach Existenz oder Inhalt statt ! Sollte in eigenen Projekten beachtet werden.
CSVLoader - Version 2.
Aus performanten Gründen habe ich den Loader komplett überarbeitet. Datenstrukur nur durch Speicher begrenzt, ansonsten sehr schnell. Weiterhin können die einzelnen Zeilen unterschiedlich lang sein, keine feste CSV(y*x) Struktur mehrnotwendig.
CODE Version 1.
/'
(c) 2009 chutullu (chutullu2(at)yahoo(dot)de) / FreeBASIC-Portal.de
stringSplit - benötigt stringSplit.bi
Version .1
CSVLoader Datentype
CSVLoader Objekt
* Version - Kennung
* filename - Dateiname
* seperator - Trennzeichen
* filelength - Zeilenanzahl der Datei
* CSVlength - Länge der Zeile
- init(filename, seperator) - alles initialisieren
- countlines - Zeilen zählen
- loadCSV (arrayString()) - lädt CSV in Array
+ [integer] = getFileLength - gibt die Zeilenanzahl der Datei zurück
+ [integer] = getCSVLength - gibt Spaltenzahl der Datei zurück
'/
Type CSVLoader
Version As Double = 0.1
filename As String
seperator As String * 1
filelength As Integer
CSVlength As Integer
Declare Sub init (ByVal filename As String, ByVal seperator As String)
Declare Sub countLines ()
Declare Sub loadCSV (strlst() As String)
Declare Function getFileLength () As Integer
Declare Function getCSVLength () As Integer
End Type
Sub CSVLoader.init (ByVal filename As String, ByVal seperator As String)
/'
Aufruf : obj.init (filename,seperator)
Ergebnis : speichert Dateiname + Seperator, zählt Spalten
Variablen : filename-Dateiname;sperator-Trennzeichen
'/
This.filename = filename
This.seperator = seperator
This.countLines()
End Sub
Sub CSVLoader.countLines ()
/'
Aufruf : obj.countLines
Ergenis : zählt "klassisch" Zeilen einer Textdatei (d.h. Zeile für Zeile);
bestimmt weiterhin die Spaltenzahl der Datei
Variablen : f-nächste freie Dateinummer;dummy-DummyString;csvLine-stringSplit Objekt
this.filelenght-Anzahl der Zeilen,this.CSVlength-Zeilenanzahl
'/
Dim f As Integer
Dim dummy As String
Dim csvLine As splitString
f = FreeFile
This.filelength = 0
Open This.filename For Input As #f
Do: This.filelength+= 1
Line Input #f, dummy
Loop Until Eof(f)
Close #f
csvLine.spl (dummy,This.seperator)
This.CSVlength = csvLine.items
End Sub
Sub CSVLoader.loadCSV (strlst() As String)
/'
Aufruf : obj.loadCSV (arrayString)
Ergebnis : lädt Daten in ein eindimmensionales Array;
Indizierung : y * max Spalten + aktuelle Zeie
Variablen : x-aktuelle Spalte;y-aktuelle Spalte;_pos-aktuelle Adresse im array;
f-nächste freie Dateinummer;dummy-dummyString;max-max Anzahl Spalten
splitting-Liste auf aktuelle Spalten
'/
Dim x As Integer
Dim y As Integer
Dim _pos As Integer
Dim f As Integer
Dim dummy As String
Dim max As Integer
f = FreeFile
y = 0
Open this.filename For Input As #f
Do
Line Input #f, dummy
Dim splitting As splitString
splitting.spl(dummy,This.seperator)
max = splitting.items
x = 0
While splitting.Split->nxt <> 0
_pos = y * max + (max - x)
strlst(_pos) = splitting.Split->item
splitting.Split=splitting.Split->nxt
x += 1
Wend
strlst(y * max + 1 ) = splitting.Split->item
y += 1
Loop Until Eof(f)
Close #f
End Sub
Function CSVLoader.getFileLength () As Integer
/'
Ergebnis : gibt Zeilenanzahl zurück
'/
Return This.filelength
End Function
Function CSVLoader.getCSVLength () As Integer
/'
Ergebnis : gibt Spaltenanzahl zurück
'/
Return This.CSVlength
End Function
Anwendung
zu beachten ist das neben dem eigentlichen CSVLoader auch der stringSplitter benötigt wird (Programm anbei).
Die Geschwindigkeit ist relativ flott, ich denke damit lassen sich schnell auch größere Mengen in kurzer Zeit
laden und ggf. bearbeiten bzw. verändern.
#Include "stringSplit.bi"
#Include "CSVLoader.bi"
Dim wholeCSV As CSVLoader
wholeCSV.init("beispiel.csv",";")
Dim y As Integer = wholeCSV.getFileLength
Dim x As Integer = wholeCSV.CSVlength
Dim csvArray(0 To y * x) As String
wholeCSV.loadCSV(csvArray())
Dim a As Integer
Dim b As Integer
For a = 1 To y
Print a;",";
For b = 1 To x
Print csvArray(a * x + b);",";
Next
Print
Print
Next
sleep
End 0
stringSplitter
#######################################################################################################
/'
(c) 2009 chutullu (chutullu2(at)yahoo(dot)de) / FreeBASIC-Portal.de
stringSplit
Version .2
SplitList Datentype
SplitString Objekt
* Zerteilt String in mit "sperator" getrennte Teile
* Zerteilen erfolgt Byte-Weise
* einfache stackListe (filo)
Struktur
* toSplit As String - String welcher zerteilt werden soll
* seperator As String - Trenner
* Split As SplitList Ptr - Liste
* items As Integer - Anzeil der Strings in der Liste
- spl (string2split, seperator) - zerteilt die Liste
- addString (istring) - fügt Element an die Liste an
'Anwendung
Dim splitting As splitString
Dim csvLine As String = "52;27.12.2008;24;11;31;16;13;3;6;0;57.529.108,50;0;4.759.241,90;8;287.645,50;53;27.136,30;2036;1.836,60;6040;95,20;98986;29,00;138499;16,60;1592121;7,90"
splitting.spl(csvLine,";")
Dim array (1 To splitting.items) As String
Dim a As Integer
a = 0
While splitting.Split->nxt <> 0
array(splitting.items-a) = splitting.Split->item
splitting.Split=splitting.Split->nxt
a+=1
Wend
array(1) = splitting.Split->item
For a = 1 To UBound (array)
Print a, array(a)
Next
Sleep
'/
Type SplitList
item As String
nxt As SplitList Ptr
End Type
Type splitString
Version As Double = 0.2
toSplit As String
seperator As String * 1
Split As SplitList Ptr
items As Integer
Declare Constructor ()
Declare Sub spl (ByVal string2split As String, ByVal seperator As String)
Declare Sub addString (ByVal istring As String)
End Type
Constructor splitString ()
This.Split = 0
This.items = 0
End Constructor
Sub splitString.spl (ByVal string2split As String, ByVal seperator As String)
/'
Aufruf : obj.spl ("asdf,gadsfg,asfas",",")
Ergebnis : zerteilt übergebenen String in mit seperator getrennte Teile
Variablen : a-Laufvariable; char-einzelnes Zeichen; dummy-Dummy-String
'/
Dim a As Integer
Dim char As String * 1
Dim dummy As String
This.toSplit = string2split
This.seperator = seperator
For a = 1 To Len(This.toSplit) 'solange bis ende der zeichenkette ereicht
char = This.toSplit[a-1] ' zeichen = zeichnkette[a]
If char = This.seperator Then ' falls zeichen = seperator
If Len (dummy) = 0 Then dummy = "0" ' 0-String verhindern (stack overflow)
This.addString (dummy) ' string an Liste hängen
This.items += 1 ' items zählen
dummy = "" ' dummy = "" und weiter
Else ' falls nicht
dummy += char ' zeichen zu dummy zählen
EndIf
Next
End Sub
Sub splitString.addString (ByVal istring As String)
/'
Aufruf : obj.addString ("adsfa")
Ergebnis : fügt String vorn an die Liste an
Variablen : istring-neuer String; this.Split-Liste
dummy-neues Listenelement
'/
If This.Split = 0 Then 'falls Liste leer
' liste anlegen
This.Split = Callocate (SizeOf ( SplitList ))
This.Split->item = istring
This.Split->nxt = 0
Else 'falls nicht
Dim dummy As SplitList Ptr ' neues Element erzeugen
dummy = Callocate (SizeOf ( SplitList ))
dummy->item = istring
dummy->nxt = This.Split ' Element nach vorn schieben
This.Split = dummy ' Anfang der Liste = neues Element
EndIf
End Sub
CODE Version 2.
Type toExplode
Const version = 2.02
array As String Ptr
csv As String
lenght As UShort
Declare Sub split (ByVal Istring As String, ByVal Isep As String)
Declare Sub arrayFree ()
End Type
Sub toExplode.split (ByVal Istring As String, ByVal Isep As String)
/'
Ergebnis : Formatiert einen CSV String =>
Beispiel
csv := "ab;abc;abcd" => csv := chr(2)+"ab"+chr(3)+"abc"+chr(4)+"abcd"
Länge String 1 --------+ | | | | |
String 1 --------------+ | | | |
Länge String 2 --------------------+ | | |
String 2 --------------------------+ | |
Länge String 3 ---------------------------------+ |
String 3 ----------------------------------------+
Aufruf : toExplode.split("ab;abc;abcd",";")
Variable : a=Laufvar.; str_len=Länge des Strings;ct=Länge Teilstring&akteller Arrayeintrag
items=Länge des Vektors; dummy=DummyString; Istring=Eingangsstring; Isep=Seperator
'/
Dim a As UShort 'Laufvariable
Dim b As UShort
Dim str_len As UShort 'Länge des Strings
Dim ct As UShort 'Länge Teilstring
Dim items As UShort 'Anzahl der Arrayeinträge
Dim dummy As String = Istring 'dummy
str_len = Len(dummy)
items Xor= items
For a = 0 To str_len - 1
b = str_len-a
If Mid(dummy,b,1) = Isep Then
Mid(dummy,b,1) = Chr(ct)
ct Xor= ct
items += 1
Else
ct += 1
EndIf
Next a
dummy = Chr(ct) + dummy
This.lenght = items + 1
This.csv = dummy
This.array = Callocate (SizeOf(String) * This.lenght)
ct Xor= ct
For a = 0 To str_len - 1
This.array[ct] = Mid(dummy,2+a,dummy[a])
a += dummy[a]
ct += 1
Next a
End Sub
Sub toExplode.arrayFree ()
/'
Ergebnis : gibt Speicher frei
Aufruf : toExplode.arrayFree ()
Variable : toExplode.array[]-Array welches aufgelöst wird
'/
DeAllocate (This.array)
This.csv = ""
This.lenght = 0
End Sub
Type CSV
Const Version = 2.0
csv_matrix As toExplode Ptr
csv_lines As String Ptr
y As UInteger
x As UInteger
Declare Sub oFile (ByVal filename As String, ByVal sep As String)
End Type
Sub CSV.oFile (ByVal filename As String,ByVal sep As String)
/'
Ergebnis : lädt ganze CSV
Aufruf : [toExplode].oFile("dateiname.csv",";")
Variablen : a,b - Laufvariablen; f-Dateinummer; dummy-String;ex - Dummy
csv_lines - alle Zeilen als String; csv_matrix - Datei als Matrix
filename - dateiname; sep - Trennzeichen
'/
Dim a As UInteger
Dim b As UInteger
Dim f As Integer
Dim dummy As String
Dim ex As toExplode
f = FreeFile
Open filename For Input As #f
Line Input #f, dummy
ex.split (dummy,sep)
Seek #f, 1
This.x = ex.lenght
ex.arrayFree
a Xor= a
Do: a+= 1
Line Input #f, dummy
Loop Until Eof(f)
Seek #f, 1
This.csv_lines = Callocate (SizeOf(String) * a)
This.y = a
a Xor= a
Do:
Line Input #f, dummy
This.csv_lines[a] = dummy
a+=1
Loop Until Eof(f)
Close (f)
This.csv_matrix = Callocate (SizeOf(toExplode) * This.y)
For a = 0 To This.y-1
This.csv_matrix[a].split(This.csv_lines[a],sep)
Next a
Exit Sub
noOpen:
Print "file not found"
End -1
ed:
Print "hier"
End Sub
/'Anwendung'/
Dim test As CSV
Dim a As Integer
Dim b As Integer
test.oFile("myFile.csv",";")
For a = 0 To test.y -1
For b = 0 To test.csv_matrix[a].lenght -1
Print test.csv_matrix[a].array[b];
Next b
Print
Next a
Sleep
End 0
Zusätzliche Informationen und Funktionen | |||||||
---|---|---|---|---|---|---|---|
|