Hallo Fabienne,
[...]typisches Anfängerbeispiel: DB-Funktionalität durch PHP-Skript nachgeahmt
Jeder muss mal anfangen und dazulernen....
das war kein Vorwurf, der auf Dich gemünzt war.
Im Gegensatz zu Dir wollen viele gar nicht dazulernen und glauben, dass ihr
PHP-Code völlig richtig und angemessen sei.
b) den Gesamtumsatz aus dem aktuellen Jahr
ist das die Summe der Einträge oder der zeitlich letzte Eintrag im Jahr
zeitlich der letzte
Wer lesen kann, ist klar im Vorteil. Beim aufmerksamen Lesen Deines Postings
habe ich das auch feststellen können.
Minutenbereich kommen dürfte (vernünftige Indizierung vorausgesetzt).
Gerade mal nachgemessen: Pro Datensatz zwischen 0,5 und 0,9 Sekunden!!!
Das ist verdammt viel, zu viel.
db.kunden
ID | Kundennummer | Name
1 | 12345 | Müller GmbH
2 | 932749 | Moritz AG
db.umsatz
ID | kunden_id | Umsatz | Jahr | erstellt_am
15 | 1 | 1789.12 | 2007 | 2007-01-05
16 | 1 | 1812.15 | 2007 | 2007-01-08
17 | 2 | 66.09 | 2007 | 2007-01-05
18 | 1 | 89.99 | 2008 | 2008-01-16db.kontakte
ID | kunden_id | Name | Vorname | key
1 | 1 | Meier | Fritz | no
2 | 1 | Metzger | Anton | yes
3 | 2 | Kohl | Helmut | yesErgebnis sollte sein:
Firma ; 2007 ; 2008 ; Key-ManagerMüller Gmbh ; 1812.15 ; 89.99 ; Metzger
Moritz AG ; 66.09 ; ; Kohl
OK, der Reihe nach:
Ein paar Anmerkungen zu Feldnamen:
Reservierte Worte wie "key" zu verwenden, ist keine gute Idee.
Es ist bei generiertem Code immer eine gute Idee, sicherheitshalber alle
Namen von Tabellen und Spalten zu maskieren. Bei MySQL ist der Backtick das
Maskierungszeichen.
Punkte in Spaltennamen zu verwenden, ist eine ganz extrem schlechte Idee.
Die ist noch schlechter als die Verwendung von reservierten Worten. Punkte
trennen bei den diversen SQL-Dialekten Datenbanken, Schemata, Tabellen und
Spaltennamen bei vollqualifizierten Namen.
1. Schritt: Ermittle die Key-Manager der Kunden:
SELECT
kunden.Name AS Firma, -- mit kann man freundliche Namen vergeben
kontakte.`key` AS `Key-Manager` -- key ist ein Schlüsselwort und muss daher
-- maskiert werden. Minuszeichen sind auch
-- nicht gut :-)
FROM
kunden
LEFT JOIN -- Wir nehmen auch Firmen mit, die uns
kontakte -- keinen Key-Manager genannt haben
ON
kunden.id = kontakte.id_kunden
2. Schritt: Ermittle den Umsatz der Kunden im Jahr 2007:
Das erfordert eine korrelierte Unterabfrage, siehe dazu z.B. dieses Archivposting:
SELECT -- Gib mir
u.kunden_id, -- die id des Kunden
u.umsatz -- und seinen Umsatz
FROM -- aus der Tabelle
umsatz u -- umsatz, die ich über das Alias u anspreche
WHERE -- wobei nur der Umsatz angezeigt wird,
u.erstellt_am = ( -- bei dem das Erstellungsdatum
SELECT --
MAX(um.erstellt_am) -- das maximale und somit neueste Datum
FROM
umsatz um -- in der Tabelle umsatz, die hier über
-- um angesprochen wird
WHERE -- für
um.kunden_id = u.kunden_id -- jede kunden_id
AND Jahr = 2007 -- und das Jahr 2007
)
3. Der Umsatz der Kunden für das Jahr 2008 kann analog ermittelt werden.
4. Nun bauen wir die Jahresumsätze ein.
Durch einen LEFT JOIN auf die Jahresumsätze wird berücksichtigt, dass auch
Kundendaten angezeigt werden, von Kunden, die in wenigstens einem der Jahre
keinen Umsatz gemacht haben (z.B. Neukunden)
SELECT
kunden.Name AS Firma,
u2007.umsatz as `Umsatz 2007`, -- Aussagekräftige Spaltenüberschriften,
u2008.umsatz as `Umsatz 2008`, -- die Maskierung erfordern
kontakte.`key` AS `Key-Manager`
FROM
kunden
LEFT JOIN -- Wir nehmen auch Firmen mit, die uns
kontakte -- keinen Key-Manager genannt haben
ON
kunden.id = kontakte.id_kunden
LEFT JOIN ( -- will ich Daten aus einem Subselect,
SELECT -- das ich als "Tabelle" anspreche, so
u.kunden_id,
u.umsatz
FROM
umsatz u
WHERE
u.erstellt_am = (
SELECT
MAX(um.erstellt_am)
FROM
umsatz um
WHERE
um.kunden_id = u.kunden_id
AND Jahr = '2007'
)
) u2007 -- muss ich dafür Namen vergeben.
ON kunden.id = u2007.kunden_id
LEFT JOIN (
SELECT
u.kunden_id,
u.umsatz
FROM
umsatz u
WHERE
u.erstellt_am = (
SELECT
MAX(um.erstellt_am)
FROM
umsatz um
WHERE
um.kunden_id = u.kunden_id
AND Jahr = '2008' -- In MySQL kann und sollte man auch Zahlen
-- als Zeichenketten übergeben
)
) u2008
ON kunden.id = u2008.kunden_id
sollte das gewünschte Ergebnis liefern, MySQL 4.1.x vorausgesetzt.
Getestet (mit anderen Daten) mit MySQL 5.0.45
Für die Performance wichtig sind Indexe für die Spalten kunden_id in den
Tabellen umsatz und kontakte.
Anschließend kannst Du die Daten mit PHP wie gewohnt ausgeben.
Freundliche Grüße
Vinzenz