webentwicklung-frage-antwort-db.com.de

Welche SQL-Abfrage ist besser, MATCH AGAINST oder LIKE?

Um die Datenbank nach Zeilen zu durchsuchen, die beide Schlüsselwörter "foo" UND "bar" in einer der Spalten "foo_desc" und "bar_desc" enthalten, würde ich Folgendes tun:

SELECT * 
FROM t1 
WHERE MATCH (t1.foo_desc, t2.bar_desc) AGAINST ('+foo* +bar*' IN BOOLEAN MODE)

oder

SELECT * 
FROM t1 
WHERE (CONCAT(t1.foo_desc, t2.bar_desc) LIKE '%foo%') AND (CONCAT(t1.foo_desc, t2.bar_desc) LIKE '%bar%')

Ich gehe davon aus, dass der Nachteil der letzten Abfrage die Leistung ist.

Der Vorteil ist, dass die LIKE-Abfrage 'xxfoo' findet, wohingegen MATCH AGAINST dies nicht tut.

Welches ist das bevorzugte oder gibt es eine bessere Lösung?

66
Wil

Aktualisieren

Ab MySQL 5.6 und höher, InnoDB Tabellen unterstützen Match... Against.


Das erste ist viel besser. In MyISAM -Tabellen wird ein Volltextindex für diese Spalten verwendet. Der andere führt einen vollständigen Tabellenscan durch, wobei in jeder Zeile ein Concat und anschließend ein Vergleich durchgeführt wird.

LIKE ist nur dann effizient, wenn Sie es gegen Folgendes tun:

  • eine Spalte (kein Ergebnis einer Funktion, es sei denn, Ihr bestimmter Datenbankanbieter unterstützt Funktionsindizes, z. B. Oracle, und Sie verwenden sie);
  • der Beginn der Spalte (dh LIKE 'blah%' im Gegensatz zu LIKE '%blah%'); und
  • eine indizierte Spalte.

Wenn eine dieser Bedingungen nicht zutrifft, kann die SQL-Engine die Abfrage nur durch einen vollständigen Tabellenscan ausführen. Dies kann unter ungefähr 10-20 Tausend Zeilen verwendbar sein. Darüber hinaus wird es jedoch schnell unbrauchbar.

Anmerkung: Ein Problem mit MATCH unter MySQL ist, dass es nur mit ganzen Wörtern übereinstimmt, sodass eine Suche nach 'bla' nicht mit einer Spalte mit dem Wert 'blah' übereinstimmt, sondern mit einer Suche nach "bla *" wird.

63
cletus