Delphi-PRAXiS

Delphi-PRAXiS (https://www.delphipraxis.net/forum.php)
-   Datenbanken (https://www.delphipraxis.net/15-datenbanken/)
-   -   Delphi SQL optimieren (https://www.delphipraxis.net/145442-sql-optimieren.html)

Dumpfbacke 1. Jan 2010 15:49

Datenbank: Interbase • Version: 6.01 • Zugriff über: IBX

SQL optimieren
 
Hallo Leute,
kann mir jemand sagen, ob ich den SQL hier optimieren kann. Es dauer ca. 35 sec. bis das Ergebnis vorliegt.
Es liegt ein Index auf jedem Feld der Where Clausel und auf den Felder in den Joins.
Ansonsten muß ich alle Daten in eine Tabelle legen denn dann geht es schneller. Das Problem kommt von den Joins vermute ich einmal.

SQL-Code:
Select Cast(GFP.Monat as Float) as Monat,
SUM(SK.AnzahlGF) as AnzahlGF,SUM(SK.KostenHoechsterist) as KostenGf,
SUM(SK.KostenHoechsterist) / SUM(SK.AnzahlGF) as KostenJeGf
from Hauptkosten SK
Left Outer Join Teilkosten GFK on GFK.Auftragsart = SK.Auftragsart
Left Outer Join Finanzen GFP on GFP.IDTeilkosten = GFK.TeilkostenZaehler
                                              and GFP.Auftragsnummer = SK.Auftragsnummer
Left Outer Join Tabelle1 on GFP.Auftragsnummer = Tabelle1.Auftragsnummer
Where Tabelle1.AuftrageingangJahr = '2009'
and GFP.Jahr = '2009'
and SK.Auftragsart = 'Neukunde'

Group by Monat
Order by 1
Tanja

mkinzler 1. Jan 2010 16:10

Re: SQL optimieren
 
Was für einen Typ hat Monat?
Wie sehen die Tabellen aus?
Reicht es nicht das Jahr in der Hauptkostentabelle zu filtern?

alzaimar 1. Jan 2010 16:17

Re: SQL optimieren
 
Wenn du nach Teilkosten.Monat gruppierst, benötigst Du den ersten LEFT JOIN nicht, denn es gilt (wenn ich mich nicht irre*):
SQL-Code:
SELECT B.DATA, SUM(A.FOOBAR) FROM A LEFT JOIN B ON A.ID = B.ID
SQL-Code:
SELECT B.DATA, SUM(A.FOOBAR) FROM B JOIN A ON B.ID = A.ID
Das sollte eventuell ein wenig einsparen, sauberer ist es aber allemal.

*Und ich irre mich nie, wenn ich mich nicht irre.

omata 1. Jan 2010 16:37

Re: SQL optimieren
 
Wegen Nichtbeachtung gelöscht...

Dumpfbacke 1. Jan 2010 17:01

Re: SQL optimieren
 
Zitat:

Zitat von mkinzler
Was für einen Typ hat Monat?

ist ein Char Feld
Zitat:

Wie sehen die Tabellen aus?
Die Tabelle1 hat etliche Spalten mit einigem an Daten. Die anderen Tabelle nur wenige < 10 Stück
Zitat:

Reicht es nicht das Jahr in der Hauptkostentabelle zu filtern?
Nein leider nicht. In der Hauptkosten ist das Datum der Abrechnung und in der Tabelle1 das Eingangsdatum vorhaden.

Diese Idee habe ich mitlerweile auch schnon gehabt.

Ich füge in der Tabelle noch zwei Splate mit dem Eingangsdatum ein und somit fallen dann einige Joins weg. Dann solte es schneller gehen.

Blup 4. Jan 2010 08:52

Re: SQL optimieren
 
Ich würde die Reihenfolge der Tabellen in der Abfrage ändern:
SQL-Code:
select cast(GFP.Monat as float) as Monat,
       sum(SK.AnzahlGF) as AnzahlGF,
       sum(SK.KostenHoechsterist) as KostenGf,
       sum(SK.KostenHoechsterist) / sum(SK.AnzahlGF) as KostenJeGf

from     Tabelle1
left join Finanzen   GFP on (GFP.Auftragsnummer   = Tabelle1.Auftragsnummer)
left join Teilkosten GFK on (GFK.TeilkostenZaehler = GFP.IDTeilkosten)
left join Hauptkosten SK on (SK.Auftragsart       = GFK.Auftragsart) and
                             (SK.Auftragsnummer    = Tabelle1.Auftragsnummer)

where (Tabelle1.AuftrageingangJahr = '2009') and
      (GFP.Jahr                   = '2009') and
      (SK.Auftragsart             = 'Neukunde')

group by Monat
order by 1

hoika 4. Jan 2010 09:12

Re: SQL optimieren
 
Hallo,

Zur Not eine SP drausmachen,
damit können die LEFT JOINS wegfallen.


Bei IB könntest du deine Abfrage auch mal durch den
IBPlanalyzer (google) schicken,
um festzustellen, wo es genau hängt.

Left Joins sind bei IB/FB übrigens immer langsamer als (Inner) Joins,
wenn NULL-Werte "gefunden" werden.

Deshalb sollten Sie vermieden werden.
Man könnte zum Bsp. Dummy-Einträge in den entsprechenden Tabelleb erzeugen
und dann (Inner) Joins nehmen.


Heiko

rwachtel 4. Jan 2010 09:51

Re: SQL optimieren
 
Zitat:

Zitat von omata
Wegen Nichtbeachtung gelöscht...

Kindergarten?

Blup 4. Jan 2010 14:00

Re: SQL optimieren
 
Zitat:

Zitat von hoika
Left Joins sind bei IB/FB übrigens immer langsamer als (Inner) Joins,
wenn NULL-Werte "gefunden" werden.

Das möchte ich so pauschal nicht stehen lassen.
Left Joins können ein gutes Werkzeug zur Optimierung sein.
Natürlich ist es etwas schwieriger eine Abfrage über mehrere Tabellen mit "left join" optimal zu gestalten.
Dazu muss man die Tabellenstruktur(welcher Index usw.) schon gut kennen.
Auf jeden Fall solte man sich den resultierenden Plan anschauen oder im schlimmsten Fall selbst vorgeben.

omata 4. Jan 2010 20:16

Re: SQL optimieren
 
Zitat:

Zitat von rwachtel
Zitat:

Zitat von omata
Wegen Nichtbeachtung gelöscht...

Kindergarten?

Nö! Bin nur nicht so menschenverachtend...


Alle Zeitangaben in WEZ +1. Es ist jetzt 21:21 Uhr.

Powered by vBulletin® Copyright ©2000 - 2024, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024 by Thomas Breitkreuz