php.de

Zurück   php.de > Webentwicklung > Datenbanken

Datenbanken SQL und Co

Antwort
 
LinkBack Themen-Optionen Thema bewerten
Alt 12.10.2011, 16:41  
Neuer Benutzer
 
Registriert seit: 10.10.2011
Beiträge: 13
PHP-Kenntnisse:
Anfänger
Aldaris befindet sich auf einem aufstrebenden Ast
Standard [Erledigt] Fehler #1111 bei Summenbildung

Hallo Forum,

ich habe wieder einmal ein Problem mit einer MySQL Berechnung und hoffe, dass ihr mir helfen könnt.

Ich habe eine Vielzahl von Produkten (in einer Datenbank) und berechne daraus einen Warenkorb nach Laspeyers(http://de.wikipedia.org/wiki/Preisindex#Laspeyres-Index). Die Preisentwicklung dieses Indexes möchte der Preisentwicklung eines bestimmten Produktes aus einer anderen Datenbank gegenüberstellen, welches in einer separaten Datenbank und nicht in der Warenkorb-Datenbank enthalten ist. Ich habe Preise und Mengen von den Artikeln in der Datenbank gespeichert und komme pro Einzelperiode auch zu dem richtigen Ergebnis.

Allerdings klappt es nicht, die Summe zu berechnen, ich bekomme immer den Fehler "#1111 - Invalid use of group function" - egal, was ich versuche. Als MySQL Version kommt 5.0.45 zum Einsatz.

Hier ist die Datenbank:

Code:
Tabelle Warenkorb
Produkt     Preis     Menge     Datum
A             10         10          12.10.2011
B             11          5          12.10.2011
C             13          1          12.10.2011
A             11          8          11.10.2011    

usw.

Code:
Tabelle Produkttabelle
Produkt     Preis         Datum
X             15             12.10.2011
X             10             11.10.2011
X             11             10.10.2011
X             11              9.10.2011    

usw.
Die Einzelabfrage für die einzelnen Tage funktioniert so:

Code:
SELECT
  n.Datum,
  ((((n.Preis + o.Preis) - (n.Preis*2))/n.Preis) ) - ((SUM(np.Preis * np.Menge) / SUM(op.Preis * np.Menge)) -1 ) AS difference
FROM
  Produkttabelle n JOIN Produkttabelle o Join Warenkorb np JOIN Warenkorb op
    ON n.Produkt=o.Produkt
    AND op.Produkt=np.Produkt
    AND n.Datum=np.Datum
    AND o.Datum=op.Datum
    AND n.Datum=o.Datum + INTERVAL 1 DAY
    AND np.Datum=op.Datum + INTERVAL 1 DAY

GROUP BY
  n.Datum DESC,
  n.Produkt ASC
Hat jemand eine Idee, wie ich den Code modifizieren müsste, um eine funktionierende Summe zu bekommen?

Vielen Dank und viele Grüße

Aldaris
Aldaris ist offline   Mit Zitat antworten
Sponsor Mitteilung
PHP Code Flüsterer

Registriert seit: 21.08.2005
Beiträge: 4682
PHP-Kenntnisse:
Fortgeschritten

Alt 12.10.2011, 17:19  
Erfahrener Benutzer
 
Registriert seit: 19.06.2009
Beiträge: 837
PHP-Kenntnisse:
Fortgeschritten
Jens Clasen ist einfach richtig nettJens Clasen ist einfach richtig nettJens Clasen ist einfach richtig nettJens Clasen ist einfach richtig nettJens Clasen ist einfach richtig nett
Standard

Versteh ich nicht. Ich kann noch nicht nachvollziehen, wofür Du da SUM() und Group By benötigst. Wie genau sieht das gewünschte Ergebnis zu Deinen Rohdaten aus?

Gruß Jens
Jens Clasen ist offline   Mit Zitat antworten
Alt 12.10.2011, 17:26  
Neuer Benutzer
 
Registriert seit: 10.10.2011
Beiträge: 13
PHP-Kenntnisse:
Anfänger
Aldaris befindet sich auf einem aufstrebenden Ast
Standard

Hi Jens,

vielen Dank für Deine Antwort.

der Quellcode aus dem Thread gibt die Tagespreisdeltas zwischen dem Warenkorb und dem Produkt aus. Prinzipiell brauche ich dazu das "n.Produkt ASC" nicht, das Datum benötige ich aber für die Sortierung nach dem Datum.

Die SUM() innerhalb der Berechnung benötige ich, da sich der Preisindex ja aus der Summe der Preise und Menge des Warenkorbes berechnet.

Das Ergebnis, was ich nun haben möchte, sollte ein einziger Wert sein: nämlich die Summe aller Tagespreisdeltas zwischen dem Warenkorb und dem Produkt.

Viele Grüße

Aldaris
Aldaris ist offline   Mit Zitat antworten
Alt 12.10.2011, 23:36  
Erfahrener Benutzer
 
Registriert seit: 19.06.2009
Beiträge: 837
PHP-Kenntnisse:
Fortgeschritten
Jens Clasen ist einfach richtig nettJens Clasen ist einfach richtig nettJens Clasen ist einfach richtig nettJens Clasen ist einfach richtig nettJens Clasen ist einfach richtig nett
Standard

So langsam sickert es ein bißchen, aber:

a) Eine einzelne Zahl kannst Du nicht sortieren. Wozu also das Datum?

b) Warum die ganzen Cross Joins? Einzelne Inner Joins wären um einiges lesbarer.

c) Warum nimmst Du den Vortag als die basisperiode? Da kann doch gar kein richtiger Laspeyres-Index bei raus kommen. Die muss doch irgendwo fest definiert sein.

d) Fehlt da nicht noch was in Deiner Gruppierklausel? Was ist mit der fehlenden funktionalen Abhängigkeit von o zu den Selectklausel-Daten?

e) Du willst eine Summe über mehrere Summen (bzw. in Deinem Fall Summenquotienten) bilden. Das geht an der Stelle nur, wenn Du ein Select über die Ergebniswerte Deines Selects bildest.

Gruß Jens
Jens Clasen ist offline   Mit Zitat antworten
Alt 13.10.2011, 08:52  
Neuer Benutzer
 
Registriert seit: 10.10.2011
Beiträge: 13
PHP-Kenntnisse:
Anfänger
Aldaris befindet sich auf einem aufstrebenden Ast
Standard

Hallo Jens,

vielen Dank für Deine Hilfe

a) Der Code beinhaltet nur die Einzelwerte der Preisdifferenzen, daher die Sortierung nach Datum.

b) Falls Du eine lesbarere Idee hast, das Problem umzusetzen, bin ich für Ratschläge dankbar. Ich gucke mir das mit den Inner Joints mal an.

c) Ein Index bei einer täglichen Betrachtung macht schon Sinn, die Betrachtungsperioden können frei gewählt werden. Die tägliche Betrachtung hat vor allem den Vorteil, dass die fixe Menge täglich neu in den Index einfließt. Wenn man das über ein Jahr betrachtet, beziehen sich die neuen Preise immer auf die Menge des Jahres davor, was zu Verzerrungen führen könnte.

d) Der Code funktioniert so einwandfrei, was meinst Du mit der fehlenden Klausel?

e) Ich benötige einfach die Summe der Einzelwerte. Wie gesagt, der Code spuckt die Einzelwerte aus, ich benötige nur noch die Summe dieser Einzelwerte und bekomme das einfach nicht hin.

Viele Grüße

Aldaris

Geändert von Aldaris (13.10.2011 um 09:38 Uhr).
Aldaris ist offline   Mit Zitat antworten
Alt 13.10.2011, 10:19  
Erfahrener Benutzer
 
Registriert seit: 19.06.2009
Beiträge: 837
PHP-Kenntnisse:
Fortgeschritten
Jens Clasen ist einfach richtig nettJens Clasen ist einfach richtig nettJens Clasen ist einfach richtig nettJens Clasen ist einfach richtig nettJens Clasen ist einfach richtig nett
Standard

Zu c) Ja - und genau das ist die Idee hinter Laspeyres. Durch Deine Variablisierung des Bezugszeitpunktes misst Du nicht mehr die Preisentwicklung. Viel mehr sorgt eine schwankende Nachfrage nach einem Produkt dafür, dass sich der Preiseinfluss auf den Warenkorb für das eine Produkt auch andauernd verändert.

Zu a), b) und e):

Code:
SELECT
  SUM(b.difference)
FROM
(
  SELECT
    n.Datum,
    ((((n.Preis + o.Preis) - (n.Preis*2))/n.Preis) ) - ((SUM(np.Preis * np.Menge) / SUM(op.Preis * np.Menge)) -1 ) AS difference
  FROM
    Produkttabelle n /* Produktdaten zum Stichtag */
      INNER JOIN Produkttabelle o /* Vortag-Daten */
        ON n.Produkt=o.Produkt
          AND n.Datum=o.Datum + INTERVAL 1 DAY
      INNER JOIN Warenkorb np /* Warenkorb-Daten zum Stichtag */
        ON n.Datum=np.Datum
      INNER JOIN Warenkorb op /* Warenkorb-Daten zum Vortag */
        ON op.Produkt=np.Produkt
          AND o.Datum=op.Datum
          AND np.Datum=op.Datum + INTERVAL 1 DAY
  GROUP BY
    n.Datum
    n.Produkt ASC
)
zu d)
Die funktionale Abhängigkeit zwischen n und o ergibt sich ausschließlich durch die Tabellenreferenz und durch die Tatsache, dass es in Deiner Produkttabelle pro Tag nur einen Datensatz gibt. Wenn eine funktionale Abhängigkeit nicht durch die Definition gegeben ist, dann müssen alle funktional unabhängigen Daten aus der Select-Klausel auch in der Gruppierklausel auftauchen.

MySQL ist sowas relativ egal - wenn mehrere Werte in einem solchen Fall in Frage kommen, dann verwendet MySQL einfach irgendeinen davon. Durch Deine Daten gibt es nur einen Wert, also wird schon mit dem richtigen gerechnet. In einem anderen DBMS kann Dir sowas aber duchaus auch um die Ohren fliegen. Zumindest ein o.Preis gehört damit auf jeden Fall noch in die Gruppierklausel. Der Vollständigkeit halber, würde ich n.Preis da sogar auch noch mit rein schreiben. (Ist aber mehr Kosmetik und guter Stil, als wirklich notwendig)

Gruß Jens
Jens Clasen ist offline   Mit Zitat antworten
Alt 13.10.2011, 11:37  
Neuer Benutzer
 
Registriert seit: 10.10.2011
Beiträge: 13
PHP-Kenntnisse:
Anfänger
Aldaris befindet sich auf einem aufstrebenden Ast
Standard

Hi Jens,

vielen Dank für Deinen Code und Deine großartige Hilfe. Hinter der letzten Klammer fehlt noch ein "AS b" und beim GROUP BY ein Komma. Dann funktioniert der Code perfekt

Code:
SELECT
  SUM(b.difference)
FROM
(
  SELECT
    n.Datum,
    ((((n.Preis + o.Preis) - (n.Preis*2))/n.Preis) ) - ((SUM(np.Preis * np.Menge) / SUM(op.Preis * np.Menge)) -1 ) AS difference
  FROM
    Produkttabelle n /* Produktdaten zum Stichtag */
      INNER JOIN Produkttabelle o /* Vortag-Daten */
        ON n.Produkt=o.Produkt
          AND n.Datum=o.Datum + INTERVAL 1 DAY
      INNER JOIN Warenkorb np /* Warenkorb-Daten zum Stichtag */
        ON n.Datum=np.Datum
      INNER JOIN Warenkorb op /* Warenkorb-Daten zum Vortag */
        ON op.Produkt=np.Produkt
          AND o.Datum=op.Datum
          AND np.Datum=op.Datum + INTERVAL 1 DAY
  GROUP BY
    n.Datum,
    n.Produkt ASC
) AS b
Zu den Anmerkungen zur Indexberechnung mache ich mir nochmal Gedanken. Du hast natürlich Recht, dass der Indexs durch die Basisänderung immer geändert wird. Ich muss schauen, ob das mit meinem Projekt in Einklang zu bringen ist.

Vielen Dank und viele Grüße

Aldaris
Aldaris ist offline   Mit Zitat antworten
Antwort


Themen-Optionen
Thema bewerten
Thema bewerten:

Forumregeln
Es ist dir nicht erlaubt, neue Themen zu verfassen.
Es ist dir nicht erlaubt, auf Beiträge zu antworten.
Es ist dir nicht erlaubt, Anhänge hochzuladen.
Es ist dir nicht erlaubt, deine Beiträge zu bearbeiten.

BB-Code ist an.
Smileys sind an.
[IMG] Code ist an.
HTML-Code ist aus.
Trackbacks are an
Pingbacks are an
Refbacks are an
Gehe zu

Ähnliche Themen
Thema Autor Forum Antworten Letzter Beitrag
[Erledigt] Zip Archive mit PHP erstellen - Kein Fehler, aber ZIP Archiv ist nicht da robat PHP Tipps 2010 34 09.03.2011 20:17
[Erledigt] session_start - Fehler Schmuse PHP Einsteiger 6 03.03.2011 13:42
Sqlite3 "Update", Fehler bei mehr als 1 "Set" Anweisung skerge12 Datenbanken 4 21.12.2010 09:45
Funktion rename() auf USB-Festplatten bringt Fehler Wing PHP Tipps 2010 13 16.07.2010 23:00
MySQL: Fehler 10046 keine Datenbank ausgewählt aschunk Datenbanken 5 22.04.2010 12:27
[Erledigt] Syntax Error - Wo ist der Fehler? Extremefall PHP Tipps 2009 5 14.12.2009 17:46
[Erledigt] vista, windows update Fehler 80070422 Screeze Off-Topic Diskussionen 3 23.09.2009 18:24
[Erledigt] Fehler bei Array ausgabe newWorldOrder PHP Tipps 2009 2 23.02.2009 17:29
Frage: Suche Fehler in diesem Script... PHP Tipps 2005-2 14 25.10.2005 19:24
[Erledigt] Seite wird nicht angezeigt, untersch. Fehler bei IE/FF/Safar PHP-Fortgeschrittene 19 31.05.2005 14:52
Blöder MySQL Fehler PHP Tipps 2005 3 15.05.2005 03:14
Fehlermeldung - aber kein fehler... Tschuu HTML, Usability und Barrierefreiheit 16 14.03.2005 15:56
Wo liegt der fehler?? PHP-Fortgeschrittene 5 22.12.2004 09:54
array_push nur in begrenzter Anzahl ausführen ? PHP Tipps 2004 2 07.09.2004 09:05

Besucher kamen über folgende Suchanfragen bei Google auf diese Seite
fehler 1111, warenkorb summe berechnen, the day group rechnung, 1111 invalid use of group function mysql update set where, mysql sum mit differenz, fehler bei summenbildung, mysql 1111, bildung einer summe in mysql tabelle, mysql fehlercode 1111, mysql join summe, php summe aller mengen, mysql sum #1111, php date 1111, mysql join on \invalid use of group function\, mysql #1111 - invalid use of group function, 1111 invalid use of group function, php 1111

Alle Zeitangaben in WEZ +2. Es ist jetzt 14:53 Uhr.




Powered by vBulletin® Version 3.7.2 (Deutsch)
Copyright ©2000 - 2012, Jelsoft Enterprises Ltd.
Search Engine Optimization by vBSEO 3.2.0
Aprilia-Forum, Aquaristik-Forum, Liebeskummer-Forum, Zierfisch-Forum, Geizkragen-Forum