Autor Beitrag
Sylvus
ontopic starontopic starontopic starontopic starontopic starontopic starhalf ontopic starofftopic star
Beiträge: 195



BeitragVerfasst: So 12.04.09 13:41 
Hi Leute, also ich hab ne "Datenbank"! Die besteht immer aus einem User und ein paar Produkten...
Jetzt hatte ich das ganze so in einer Textdatei vorliegen:

ausblenden Quelltext
1:
2:
3:
4:
5:
6:
7:
User0 - Produkt 1
User1 - Produkt 1
User1 - Produkt 2
User2 - Produkt 1
User2 - Produkt 2
User2 - Produkt 3
...


und hab daraus jetzt eine IniDatei gemacht die so aussieht:

ausblenden Quelltext
1:
2:
3:
4:
5:
6:
7:
8:
9:
10:
11:
12:
13:
[0]
name=User0
Pr0=Produkt1
[1]
name=User1
Pr0=Produkt1
Pr1=Produkt2
[2]
name=User2
Pr0=Produkt1
Pr1=Produkt2
Pr2=Produkt3
...


Insgesammt sind das 1000 User mit ungefähr 16 000 Produkten! Jetzt bin ich grad dabei die IniFile in ein Array/Record einzulesen und es dauert verdammt lange! Jetzt wollte ich fragen woran das liegt :)
Ist die Inidatei langsamer beim durchgehen als die textdatei? Oder liegt es an der Struktur oder doch an meinem Record? Hier dafür nochmal der DelphiCode:

ausblenden Delphi-Quelltext
1:
2:
3:
4:
5:
6:
7:
8:
9:
10:
11:
12:
13:
14:
   Data = record
      user: string;

   Lib: array of Data;
...
   ini := TIniFile.create(ExtractFilePath(ParamStr(0)) + 'daten.ini');
   I := 0;
   Setlength(Lib, 1);
   while Ini.ReadString(inttostr(I), 'user''no name') <> 'no name' do begin
      Lib[I].user := Ini.ReadString(inttostr(I), 'user''no name');
      //NamesBox.Items.Add(Lib[I].user); //nicht der Grund, kann ich auch auskommentieren
      Inc(I); Setlength(Lib, length(Lib) + 1); //ist das der Grund??
   end;
   ini.Free;

Das dauert jetzt schon ungefähr 15 sekunden und dabei lese ich nur die Namen und noch nichtmal die Produkte ein...darum mach ich mir grad Sorgen!
Vll könnt ihr ja helfen!
Viele Grüße Sylvus

//edit
hab das ganze jetzt mit den Produkten mitrein genommen und jetzt dauert das starten irgendwie extrem lange, warte grad schon 5 min. und hab immer noch kein Fenster (procedure liegt im oncreate ereignis)!
Regan
ontopic starontopic starontopic starontopic starontopic starhalf ontopic starofftopic starofftopic star
Beiträge: 2157
Erhaltene Danke: 72


Java (Eclipse), Python (Sublimetext 3)
BeitragVerfasst: So 12.04.09 13:56 
Also erstmal würde ich dir von der TIniFile abraten. Ich nehme oft: FastIniFiles. Oder du nimmst die dort auch erwähnten MemIniFiles.
Dann denke ich, wie du schon geschrieben hast, dass die Arraylänge erweitern so lange dauert. Der Grund: Es wird jedes Mal ein neues Array erstellt, welches um 1 länger ist, und dann werden die alten Daten reinkopiert.
Lösung: Mach dir entweder einen Key, der die Anzahl der Benutzer speichert; oder erhöhe die Länge um z. B. 4 bei jedem Mal. Lezteres ist aber nur eine Notlösung.
jaenicke
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starofftopic star
Beiträge: 19315
Erhaltene Danke: 1747

W11 x64 (Chrome, Edge)
Delphi 11 Pro, Oxygene, C# (VS 2022), JS/HTML, Java (NB), PHP, Lazarus
BeitragVerfasst: So 12.04.09 14:00 
Bei 1000 Benutzern und 16000 Produkten geht kaum ein Weg an einer richtigen Datenbank vorbei. Nur damit kannst du solche Datenmengen gut sortieren und filtern usw., das dauert mit Inis oder ähnlichen Lösungen einfach zu lange (und hat ja auch andere Nachteile).

MySQL, SQLite, usw., da gibt es viele Möglichkeiten.
Sylvus Threadstarter
ontopic starontopic starontopic starontopic starontopic starontopic starhalf ontopic starofftopic star
Beiträge: 195



BeitragVerfasst: So 12.04.09 14:08 
hay, also erst einmal zu den einfachen Sachen :)

An Setlength liegt es glaub ich nicht, hab grad getestet und keinen merklichen Unterschied festgestellt.
Die Datenbanklösung wäre bestimmt die schlauste, allerdings muss ich das morgen fertig bekommen und hab noch nie mit Datenbanken gearbeitet, darum denke ich, dass es für mich in der Zeit einfach so nicht schaffbar ist.

Ich würd jetzt also mal die FastIniFiles testen :) Problem nur:

Wo bekomm ich die?

Wenn ich deinem Link folge bekomme ich zwar das richtige Thema, aber die Links dort sind alle nicht mehr gültig! Könntest du vielleicht die Unit nochmal online stellen, oder mir anders zukommen lassen?

Außerdem noch kurz die Frage, wie ich das einbinde?! Also einfach neue Unit hinzufügen, Unit auswählen bei uses eintragen und dann kann ich die Befehle auf meine "alte" IniFile anwenden?

Vielen Dank
Sylvus
jaenicke
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starofftopic star
Beiträge: 19315
Erhaltene Danke: 1747

W11 x64 (Chrome, Edge)
Delphi 11 Pro, Oxygene, C# (VS 2022), JS/HTML, Java (NB), PHP, Lazarus
BeitragVerfasst: So 12.04.09 14:12 
user profile iconSylvus hat folgendes geschrieben Zum zitierten Posting springen:
An Setlength liegt es glaub ich nicht, hab grad getestet und keinen merklichen Unterschied festgesetllt.
SetLength ist sehr langsam, wenn du das jedesmal aufrufst, merklich wird der Unterschied aber nur, wenn du in 100er Schritten oder noch mehr die Länge des Arrays veränderst.

Die andere Sache: INIs sind nicht besonders schnell, insbesondere bei derartigen Datenmengen. Wenn es um Geschwindigkeit geht, sind Lösungen, die kein Parsen der Datei benötigen, sicher schneller. Typisierte Dateien zum Beispiel. Auch wenn es natürlich mit FastIniFiles sicher schon schneller ist.
Regan
ontopic starontopic starontopic starontopic starontopic starhalf ontopic starofftopic starofftopic star
Beiträge: 2157
Erhaltene Danke: 72


Java (Eclipse), Python (Sublimetext 3)
BeitragVerfasst: So 12.04.09 14:15 
user profile iconSylvus hat folgendes geschrieben Zum zitierten Posting springen:

Wo bekomm ich die?

Tja. Look up :wink: .

user profile iconSylvus hat folgendes geschrieben Zum zitierten Posting springen:
Außerdem noch kurz die Frage, wie ich das einbinde?! Also einfach neue Unit hinzufügen, Unit auswählen bei uses eintragen und dann kann ich die Befehle auf meine "alte" IniFile anwenden?

Nicht ganz. Das aufrufen der Sektionen geht mit EnterSection. Dafür brauchst du die dann nicht mehr im Abfragen der Werte hinschreiben.
Sylvus Threadstarter
ontopic starontopic starontopic starontopic starontopic starontopic starhalf ontopic starofftopic star
Beiträge: 195



BeitragVerfasst: So 12.04.09 14:17 
jep, aber ich hatte jetzt "Setlength(Lib, 1056);" geschrieben und damit das ganze rausgeschafft, das einlesen hat aber trotzdem mehrer Sekunden gedauert... Lohnt es sich dann von der Performance jetzt auf typisierte Datein umzusteigen, also ich lerne gerne was neues, aber wenn ich unter Zeitdruck stehe will ich lieber nichts "umsonst" machen :) Und wenn ich jetzt meine ganze IniDatei sozuagen neu strukturieren müsste - um die Daten in eine .bat Datei zu schreiben, wäre das, für mich, ohne wirklichen Nutzen zu viel Zeitaufwand...

Vielleicht kannst du mir ja noch ein paar Infos dadrüber geben :)
Wäre sehr nett!
Lg Sylvus
Regan
ontopic starontopic starontopic starontopic starontopic starhalf ontopic starofftopic starofftopic star
Beiträge: 2157
Erhaltene Danke: 72


Java (Eclipse), Python (Sublimetext 3)
BeitragVerfasst: So 12.04.09 14:19 
Also ich an deiner Stelle würde mir mal diese einfach Datenbankunit anschauen. Die ist so einfach zu verstehen, dass das in der kurzen Zeit kein Problem sein sollte.
Sylvus Threadstarter
ontopic starontopic starontopic starontopic starontopic starontopic starhalf ontopic starofftopic star
Beiträge: 195



BeitragVerfasst: So 12.04.09 14:23 
Ok also ich mach jetzt folgendes:

- Teste schnell die FastIniFiles, sollte ja nicht so schwer sein, wenn das nicht wirklich schneller geht schau ich mir mal den Link zu der SQLite Datenbank an und wenn das alles zu schwer ist gehe ich zu den typisierten Datein über!

Vielen Dank schonmal an alle, die hier so toll geholfen haben :) Vielleicht schreib ich ja gleich noch neue Probleme, dann aber wahrscheinlich zu nem anderen Thema *g*

Wenn ihr noch was anzumerken habt, ich bin gerne offen für alles!

Viele Grüße und ein tolles Fest
Sylvus


//die FastIniFiles scheinen schonmal deutlich schneller zu sein, mache jetzt den test mit den Produkten... :)

// Die FastIni Files machen hier ganz klar das rennen, Programm braucht jetzt zum starten vll ne Sekunde, das ist schon sehr cool :) Aber ich hab Lust auf die Datenbank+typisierte Datein bekommen, werd das dann als Vergleich nach den Ferien nochmal testen, wenn der ganze Stress vorbei ist! Vielen Dank nochmal und großes Lob an Silas^^
Bye bye

//Noch ne Frage :) Die Sonderzeichen also: ò ... gehen nicht, kann man da noch was machen?
Flamefire
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starhalf ontopic star
Beiträge: 1207
Erhaltene Danke: 31

Win 10
Delphi 2009 Pro, C++ (Visual Studio)
BeitragVerfasst: So 12.04.09 16:22 
erst mal zu deiner lösung:
ausblenden Delphi-Quelltext
1:
2:
   while Ini.ReadString(inttostr(I), 'user''no name') <> 'no name' do begin
      Lib[I].user := Ini.ReadString(inttostr(I), 'user''no name');

nicht sehr sinnvoll, den eintrag 2 mal zu lesen, speicher ihn lieber zwischen
und als default-wert nimm lieber den leeren string, der beim vergleich schneller ist (logisch oder?)
dann kommst du besser, wenn du die anzahl der einträge mit speicherst. dann kannst du dein array gleich auf die richtige größe setzen und brauchst den vergleich nicht mehr (was passiert bei deiner variante beim löschen? da muss ja alles verschoben werden)

für dein problem sind datenbanken DIE lösung. die sind genau dafür da und sehr schnell.

ansonsten wenigstens typisierte datein. mehr aufwand bei der programmierung als ini-files aber deutlich schneller.