Hi Andreas,
Warum sollte man Woerter doppelt speichern? Du kannst
stattdessen die Wertigkeit mitspeichern, in einer weiteren
Spalte.
Das hatte ich jetzt Michaels Aussage entnommen, dass man nur eine Tabelle verwendet, mit je Wort => Posting_ID, und dann könnte man über Wort einen Index legen ung hätte dann auch sowas wie eine logarithmische Suche, da im Index ja auch nur jedes Wort 1 mal vorkommt,
Im Index kommt jedes Wort ziemlich oft vor - mindestens so oft, wie Du zu einem Suchbegriff verschiedene Treffer-Dokumente finden können willst.
"wort -> dokument" ist eine m:n-Beziehung.
Dein Tabellenmodell versucht, diese m:n-Beziehung durch zwei Tabellen zu realisieren, die jeweils eine 1:n-Beziehung speichern, und diese per JOIN zu verknüpfen (oder einen Übersetzungs-Schritt per separatem SQL-Statement durchführen, was auch nicht ganz unsonst ist - das könntest Du allerdings über eine Hashing-Funktion ohne Datenbankzugriff versuchen); das spart Speicher, kostet aber Zeit. Da Du gerade dabei bist, Zeit zu erkaufen, indem Du Speicher investierst, solltest Du an dieser Stelle vielleicht _nicht_ in die _entgegengesetzte_ Richtung optimieren, sondern doch lieber redundante Repräsentationen der Suchbegriffe speichern - das war meine Idee dabei.
Ich überlege halt eienn Fulltext-Index manuell in einer, bzw. 3 Tabellen nachzubilden. Das würde ich dann wenigstens verstehen und könnte das entsprechend versuchen anzupassen.
Wenn das Ganze auf einer nicht-mySQL-Datenbank auf dem Self-Server laufen soll und Du das Funktionsprinzip beibehalten willst, wird Dir eine "Emulation" von FULLTEXT durch eine eigene Tabelle nicht erspart bleiben. (Deshalb habe ich diesen Diskussions-Strang forciert.)
Woher weiß ich vorher was der User als nächstes in der DB
sucht?
Gar nicht. Warum solltest du das wissen muessen? Behalte die
durchschnittlich am meisten gebrauchten Teile permanent im
Speicher und gut.
Das ist das was sowohl mein Filesystem als auch der MySQL-Cache tut, nur wenn man sich mal so Suchanfragen ansieht, dann sind die doch sehr verschieden.
Das macht nichts.
Das Problem ist das ca. 90% der Suchanfragen sehr selten sind. Die kann man nicht alle im Cache halten,
Das ist wahr. Aber es ist nicht wirklich teuer, den Abstieg durch 10 Seiten innerhalb des Indexbaums zu machen. Es ist sehr viel teurer, 1000 Seiten voller Treffer auf der Suche nach "JavaScript"-Postings von der Festplatte zu lesen, nur um anschließend festzustellen, daß man davon 99% besser gar nicht erst gelesen hätte. Und dieses "gar nicht erst lesen" ist der Trick.
die 10% die öfter sind, gut, aber die nicht gecachten seltenen Anfragen müssen jedesmal im kompleten Index gesucht werden, der Volltext Index für den gesamten Self-Raum hätte bestimmt 250 MB, der müßte dann also komplett einmal geparst werden,
Nein. Die Knoten des Baums liegen auf separaten Bereichen der Festplatte. Du mußt wirklich nur diejenigen Teile des Indexbaums lesen, die für Deine aktuelle Suche von Interesse sind. Und das sind sehr viel weniger als 100%.
durchsucht werden und dann müßten die Daten der Ergebnisse noch aus der Tabellen-Datei von der Platte geholt werden, aber das ist dann das geringste Problem. ODer habe ich das jetzt total faslch verstanden? ODer muß der Index nicht geparst werden?
Du _navigierst_ innerhalb des Index. Die Geschwindigkeit beim Zugriff auf die gewünschten Informationen basiert exakt darauf, _nicht_ den kompletten Index lesen zu müssen, sondern sich von Ebene zu Ebene in immer tiefere Teilbäume vorzutasten. Du liest nicht zuerst den kompletten Index ein und suchst anschließend etwas in diesem - Du liest zuerst die Wurzelseite des Indexbaums und prüfst innerhalb dieser Liste, welche Seiten der 1. Ebene Du für Deinen Indexzugriff benötigst (das werden fast immer nur sehr wenige sein, etwa eine oder höchstens zwei, falls Dein Suchbegriff zufällig genau an der "Kante" zwischen zwei Teilbäumen liegt). Für die so ausgewählten Unterseiten führst Du dieselbe Operation rekursiv wieder aus.
Dabei werden die meisten Suchvorgänge dieselben Indexseiten der obersten Ebenen einlesen. Diese haben eine hohe Cache-Hit-Rate und werden deshalb vom Betriebssystem permanent im Hauptspeicher gehalten. Angenommen, der Baum adressiert eine Million Postings, hat also eine Höhe von 20 binären Knoten, dann könnte man problemlos die obersten 15 Ebenen komplett im Hauptspeicher halten, weil sie nur 1/(2^5) = 3,125% des Indexbaums ausmachen. Nur für die untersten fünf Ebenen, also ein Viertel der Index-Navigationsschritte, müßtest Du auf Seiten der Festplatte zugreifen. (Bei der Verwendung von B-Bäumen statt binären Bäumen wird das Verhältnis eher noch günstiger, vermute ich.)
Also wird beim MySQL Volltext irgendwie ein binärer Baum auf der Festplatte gespeichert, und der wird dann halt durchsucht(das meine ich mit logarithmisch im Gegensatz zum succesiven Durchsuchen einer Tabelle). Aber das müßte doch tierisch schnell sein, ist es aber nicht.
Das Finden ist immer tierisch schnell, denn seine Dauer ist unabhängig von den verwendeten Suchbegriffen - vorausgesetzt, Du verwendest kein AND zwischen mehreren MATCH()es (denn das wiederum kostet einen JOIN, und der ist ggf. sehr teuer).
Auch das Zurückliefern der gefundenen Ergebnisse ist keineswegs immer gleich schnell, denn das ist abhängig von der _Anzahl_ der gefundenen Treffer. Und da die Suche aus der Kombination von Finden und Ausliefern besteht, wird eine Suche nach "Ratzelfatz" immer schneller sein als eine Suche nach "Javascript". Und vor allem wird eine Suche nach "Ratzelfatz" schneller sein als eine Suche nach "Ratzelfatz AND JavaScript". Dieser Geschwindigkeitsunterschied muß jedoch möglichst klein werden - das muß das Ziel Deiner Generierung von SQL-Code sein.
Mach mal eine Suche nach einem Begriff, der überhaupt nicht vorkommt. Dann hast Du ein realistisches Maß für die maximale Finde-Geschwindigkeit. Anschließend sollte das Ziel darin bestehen, bei möglichst vielen Suchvorgängen relativ nahe an diese Geschwindigkeit heran zu kommen und bei möglichst vielen der rechtlichen Suchvorgänge schon vor der Suche zu erkennen, daß sie sehr langsam sein werden. Eine Suche nach "JavaScript" ohne weitere Suchbegriffe muß Deine Oberfläche erkennen und zurückweisen.
Viele Grüße
Michael
T'Pol: I meant no insult.
V'Lar: Of course not. You're simply speaking your mind ... as you always have.