[MySQL] Abfrage beschleunigen (Joins)

Steusi

Nasenbär
Hallo,

ich habe eine einfache Aufgabe, die extrem lange dauert. Ich habe zwei Tabellen und möchte einfach prüfen, ob eine Nummer (als Varchar) von TabelleA in TabelleB enthalten ist.

Ich benötige sowohl die Nummern, die enthalten sind als auch die Nummern die nicht enthalten sind. Hintergrund ist die Zuweisung von Kostenstellen zu den "Nummern"

Was ich versucht habe:
- Views erstellt um große Tabellen schmal zu halten
- Indizes über relevante Spalten gesetzt
- Subquerys genutzt um die Tabellen vorab schon zu minimieren

Doch alles brachte wenig, auf die Subquerys habe ich verzichtet und gemerkt der interne MySQL Optimizer bekommt es besser hin, daher sieht meine 1. Abfrage so schlicht aus und dauert 7 Sekunden:
SQL:
SELECT a.kostenstelle, 
             SUM(b.price)
FROM a, b 
WHERE a.nr = b.nummer 
AND b.rg_nummer = '123456'
GROUP BY a.kostenstelle
Dort ist a ein View, bei der Originaltabelle haben die relevanten Spalten einen Index.

Bei meiner zweiten Abfrage habe ich leider noch nie ein Ergebnis gesehen, es dauert einfach zu lange und der MySQL-Dienst verweigert die Arbeit:
SQL:
SELECT b.nummer, 
             b.price
FROM b 
LEFT JOIN a
ON b.nummer = a.nr
WHERE a.nr IS NULL
AND b.rg_nummer = '123456'

Alternative 1:
SQL:
SELECT bb.nummer, 
             bb.price
FROM (SELECT nummer, price FROM b WHERE rg_nummer = '123456') bb
LEFT JOIN (SELECT nr FROM a) aa
ON bb.nummer = aa.nr
WHERE aa.nr IS NULL


Alternative 2:
SQL:
SELECT b.nummer
	     b.price
FROM b
WHERE rg_nummer = '123456'
AND nummer NOT IN (
	SELECT nr
	FROM a
)

Code:
EXPLAIN
id 	select_type 	table 		type 	possible_keys 	key 		key_len 	ref 	rows 	Extra
1 	SIMPLE 			b 			ref 	rg_nummer 		rg_nummer 	26 			const 	21453 	Using where
1 	SIMPLE 			a			ALL 	NULL			NULL		NULL		NULL	279107 	Using where

Es sind gar nicht viele Datensätze, mit Subquerys müssen lediglich 3.000 Nummern mit diesen knapp 300.000 Nummern verglichen werden. Die große Zahl sollte monatlich um ca. 75.000 wachsen.

Ich hoffe jemand hat einen Tipp wie ich diese sehr simple Abfrage beschleunigen kann, mir sind alle Mittel recht! Unter 10 Sekunden würde mir schon reichen.

DANKE
 
Hallo, die Informationen sind recht dürftig. Hast du geschaut, ob die Indexe richtig gesetzt worden sind?
Code:
SELECT *
FROM (SELECT b.* FROM tabelleB b WHERE b.id NOT IN (SELECT a.id FROM tabelleA))

Hast du schon mal mit Distinct gearbeitet?
 

Neue Beiträge

Zurück