Hallo Zusammen,
ich habe eine Tabelle mit Auftragsdaten, in der ich historische Daten speichere. In dieser Tabelle sind über 2,5 Mio Datensätze. AUs diesem Grund sind die Abfragen sehr langsam (1,6-2,1 sek). Ich habe keine Idee, ob / wie ich die Tabelle schneller bekomme.
So ist die Tabelle aufgebaut:
Delphi-Quellcode:
CREATE TABLE `nedcom`.`as400archiev` (
`WAAUNR` varchar(20) NOT NULL COMMENT 'FA-Nr',
`WAAUPO` varchar(20) NOT NULL COMMENT 'FA-Zusatz',
...snip...
PRIMARY KEY (`WAAUNR`,`WAAUPO`,`OAAGNR`)
) ENGINE=MyISAM DEFAULT CHARSET=latin1 ROW_FORMAT=DYNAMIC;
Hat jemand eine Idee?
Vielen Dank
Patrick
Was der Server braucht is memory, je mehr desdo besser. Je mehr der Indexfiles und der Tabellen der Server im Speicher halten kann desdo schneller kann er Abfragen bearbeiten, denn der Zeitfresser sind die Diskzugriffe. Bei den meisten DBs kann man auch in der
DB Konfiguration festlegen, wieviel Memory der Server für die diversen Caches verwenden darf (teilweise sind das per session Einstellungen, e.g. für temporäre Daten, die bei der Bearbeitung einer Abfrage anfallen). Wenn der
DB Admin hier zu knauserig ist kann das drastische Auswirkungen auf die Performance haben.
Ansonsten ist vieles, wie schon in anderen Antworten gesagt, von der spezifischen
Query abhängig. Die besseren Datenbanken bieten eine
query plan analyzer an, mit dem man sich mal ansehen kann, wie der
query optimizer sich das Vorgehen vorstellt und was er da Zeitbedarf abschätzt. Da kann man normalerweise sofort sehen, ob vorhandene Indizes verwendet werden oder der Optimizer auf einen full table scan ausweicht (schlecht, sehr schlecht!).
Es hängt auch von der Art der
Query ab, ob die Datenbank schon Records zurückliefern kann, bevor der volle Resultset verfügbar ist. Sowas wie "distinct", "group by" oder "order by" in der
query machen das unmöglich (es sei denn, ein order by kann direkt über einen Index realisiert werden). Verwendung von Funktionen in einer WHERE-Klausel (wie concat, upper, cast, etc.) machen es unmöglich, für den Zugriff einen Index auf dem betroffenen Feld zu verwenden, selbst wenn einer existiert.
Außerdem sind select * Abfragen Gift für die Performance, wenn man eigentlich nur einen Teil der Spalten braucht. Sowas erhöht einfach das Datenvolumen, was den Speicher des Servers belastet und die Datenübertragung zum Client bremst.
Außerdem sollte man immer im Hinterkopf behalten, dass auch Abfragen bei den meisten
DB Servern in Transaktionen laufen und damit Serverresourcen belegen, bis die Abfragen geschlossen und die zugehörige Transaktion committed wurde (glücklicherweise macht das Client framework das normalerweise, wenn man eine
Query schließt). Viele Abfragen offenzuhalten ist daher etwas, mit dem man sich weder bei
DB Admins noch bei den Benutzern beliebt macht
. Leider macht das typische Delphi
RAD Design genau das...