GROUP BY > Monatsumsätze

Themen rund um den praktischen Einsatz von Firebird. Fragen zu SQL, Performance, Datenbankstrukturen, etc.

Moderator: thorben.braun

Antworten
Benutzeravatar
bibsi
Beiträge: 5
Registriert: Fr 23. Okt 2020, 10:29

Hallo Forengemeinde.

Ich arbeite schon seit Monaten an der Portierung meines alten Delphi Programms von Windows nach Lazarus Linux.
Meine Datenbank hat eine Tabelle mit dem Namen MAPPE

Code: Alles auswählen

CREATE TABLE MAPPE
(
  ID D_ID NOT NULL,
  ADRESSE_ID D_ID NOT NULL,
  ZAZI_ID D_FK_ID NOT NULL,
  PROVISIONS_ID D_FK_ID NOT NULL,
  DATUM D_DATUM NOT NULL,
  BESTELLART D_VARCHAR15,
  KORREKTUR D_DATUM,
  FREIGABE D_DATUM,
  VERSANDART D_VARCHAR15,
  AUSLIEFERUNG D_DATUM,
  GELIEFERT D_DATUM,
  BERECHNET_AM D_DATUM,
  SUMME_MAPPE D_GELD,
  REC_NUM D_INTEGERS,
  MWST D_INTEGERS,
  K_AUFTRAGNR D_VARCHAR15,
  ERTEILT_DURCH D_VARCHAR25,
  BEARBEITER D_VARCHAR25,
  CONSTRAINT PK_MAPPE PRIMARY KEY (ID)
);

mit einem View

Code: Alles auswählen

CREATE VIEW MONATSUMSATZ (JAHR, MONAT, BETRAG)
AS select
  extract(YEAR FROM berechnet_am)as Jahr,
  extract(MONTH FROM berechnet_am) as Monat,
  Summe_mappe as betrag
from mappe
where (id>-1) and (berechnet_am is not NULL);
GRANT DELETE, INSERT, REFERENCES, SELECT, UPDATE

hole ich mir die einzelnen Umsätze um sie
mit einer Sql-Abfrage

Code: Alles auswählen

Select  (monat ||  '.' || Jahr)  as Datum,
        Sum(Betrag) as Umsatz
from MonatsUmsatz
group by monat,Jahr
Order by Jahr,Monat
in ein DBChart anzeigen zu lassen.

Gibt es eine bessere Möglichkeit im VIEW Monatzumsatz gleich die richtigen werte zu bekommen (Datum nur als Jahr und Monat und die summierten Beträge)?

Für Eure Beschäftigung meines Problems danke ich schon mal :)
Zuletzt geändert von bibsi am Do 29. Okt 2020, 18:36, insgesamt 1-mal geändert.
Benutzeravatar
martin.koeditz
Beiträge: 443
Registriert: Sa 31. Mär 2018, 14:35

Hallo bibsi,

du könntest dein berechnetes Feld aus der letzten Abfrage natürlich auch direkt in die View verlegen:

Code: Alles auswählen

CREATE VIEW MONATSUMSATZ (DATUM, BETRAG)
AS select
extract(MONTH FROM berechnet_am) || '.' || extract(YEAR FROM berechnet_am) as datum,
Summe_mappe as betrag
from mappe
where (id>-1) and (berechnet_am is not NULL);
GRANT DELETE, INSERT, REFERENCES, SELECT, UPDATE
Gruß
Martin
Martin Köditz
it & synergy GmbH
Benutzeravatar
bibsi
Beiträge: 5
Registriert: Fr 23. Okt 2020, 10:29

Lieber Martin.
Dein SQL Vorschlag hat leider nicht mein gewünschtes Ergebnis gebracht.
Aber es hat meine Gedanken eine neue Richtung gegeben. ;)
Danke dafür.

das durch Deine Anregung angepaste SQLStagment hat zwar jetzt mich zum Ziel ein Stück weiter gebracht:

Code: Alles auswählen

select
extract(MONTH FROM berechnet_am) || '.' || extract(YEAR FROM berechnet_am) as datum,
sum (Summe_mappe) as umsatz

from mappe
where (id>-1) and (berechnet_am is not NULL)
group by datum;
Aber die richtige Reihenfolge ist mir noch ein Räzel ?

Code: Alles auswählen

1.2002	6582.650024
1.2003	2913.000000
1.2004	6795.000000
1.2005	10430.039978
1.2006	6718.199997
1.2007	5894.000000
1.2008	6361.500000
1.2009	8123.779978
1.2010	7156.400017
1.2011	6409.199997
1.2012	3511.000000
1.2013	4830.000000
1.2014	3530.500000
1.2015	2142.500000
1.2016	1636.000000
1.2017	1804.500000
1.2018	2752.000000
1.2019	3381.000000
1.2020	2429.000000
10.2001	11465.199976
10.2002	10533.300003
10.2004	4782.999994
Es wird ja nach Monaten sortiert, gibt's da noch eine Hilfe?
:)
Zuletzt geändert von bibsi am Do 29. Okt 2020, 18:42, insgesamt 1-mal geändert.
Benutzeravatar
martin.koeditz
Beiträge: 443
Registriert: Sa 31. Mär 2018, 14:35

Wenn ich das nun richtig verstehe, möchtest du die Ausgabe nach Jahr und dann nach Monat sortieren. Da die Sortierung alphanumerisch erfolgt, wird zunächst der Monat und dann das Jahr ausgewertet. Nun gibt es verschiedene Möglichkeiten.
  • Beide Felder tauschen (Jahr.Monat)
    Zwei Hilfspalten (Monat, Jahr) bilden
Letzteres könnte dann so aussehen:

Code: Alles auswählen

select
extract(MONTH FROM berechnet_am) || '.' || extract(YEAR FROM berechnet_am) as datum,
extract(MONTH FROM berechnet_am) as monat,
extract(year FROM berechnet_am) as jahr,
sum (Summe_mappe) as umsatz
from mappe
where (id>-1) and (berechnet_am is not NULL)
group by jahr, monat
order by extract(YEAR FROM berechnet_am) || '.' || extract(MONTH FROM berechnet_am);
Gruß
Martin
Martin Köditz
it & synergy GmbH
Benutzeravatar
bibsi
Beiträge: 5
Registriert: Fr 23. Okt 2020, 10:29

Danke das war sehr hilfreich! :)

Nur das ORDER BY am schluss ist vermutlich kontraproduktiv,
da ich vermute durch > group by jahr, monat <
wird schon richtig sortiert.

Diese Abfrage liefer das richtige Ergäbnis.

Code: Alles auswählen

select
extract(MONTH FROM berechnet_am) || '.' || extract(YEAR FROM berechnet_am) as datum,
extract(MONTH FROM berechnet_am) as monat,
extract(year FROM berechnet_am) as jahr,
sum (Summe_mappe) as umsatz
from mappe
where (id>-1) and (berechnet_am is not NULL)
group by jahr, monat

Ergebnis:
9	2001	5516.290119
10	2001	11465.199976
11	2001	11753.559967
12	2001	9707.630072
1	2002	6582.650024
2	2002	7682.420044
3	2002	8948.659912
4	2002	10248.960007
5	2002	3209.000000
6	2002	15335.820023
7	2002	9601.500001
8	2002	7213.250000
9	2002	8404.760002
10	2002	10533.300003
11	2002	4604.820007
12	2002	15123.399994
Wunderbar: Aufgabe gelöst Danke!!! :D
Zuletzt geändert von bibsi am Do 29. Okt 2020, 18:45, insgesamt 2-mal geändert.
Benutzeravatar
martin.koeditz
Beiträge: 443
Registriert: Sa 31. Mär 2018, 14:35

Nur das ORDER BY am schluss ist vermutlich kontraproduktiv,
da ich vermute durch > group by jahr, monat <
wird schon richtig sortiert.
Nein, das dies bei dir richtig sortiert ist, ist reiner Zufall. Nur mittels ORDER BY erhältst du wiederholend korrekte Ergebnisse. Aber schön, dass du nun am Ziel bist.

Gruß
Martin
Martin Köditz
it & synergy GmbH
Benutzeravatar
bibsi
Beiträge: 5
Registriert: Fr 23. Okt 2020, 10:29

martin.koeditz hat geschrieben: Sa 24. Okt 2020, 21:28
Nein, das dies bei dir richtig sortiert ist, ist reiner Zufall. Nur mittels ORDER BY erhältst du wiederholend korrekte Ergebnisse. Aber schön, dass du nun am Ziel bist.
Das mag bei Zahlenwerten sein aber in diesen Fall sind es ja Strings.
Die werden anders sortiert oder lieg ich da falsch?

Code: Alles auswählen

select
extract(MONTH FROM berechnet_am) || '.' || extract(YEAR FROM berechnet_am) as datum,
extract(MONTH FROM berechnet_am) as monat,
extract(year FROM berechnet_am) as jahr,
sum (Summe_mappe) as umsatz
from mappe
where (id>-1) and (berechnet_am is not NULL)
group by jahr, monat
order by extract(YEAR FROM berechnet_am) || '.' || extract(MONTH FROM berechnet_am);

Ergebnis:
10.2001	10	2001	11465.199976
11.2001	11	2001	11753.559967
12.2001	12	2001	9707.630072
9.2001	9	2001	5516.290119
1.2002	1	2002	6582.650024
10.2002	10	2002	10533.300003
11.2002	11	2002	4604.820007
12.2002	12	2002	15123.399994
2.2002	2	2002	7682.420044
3.2002	3	2002	8948.659912
4.2002	4	2002	10248.960007
5.2002	5	2002	3209.000000

Dort siest Du die falsche sortierung. Datum > Monat 9 kommt nach Monat 12 !?

Ich nehme an dass da die Sortierung anderst formuliert werden muss. ;)
Zuletzt geändert von bibsi am Do 29. Okt 2020, 18:55, insgesamt 1-mal geändert.
vr2
Beiträge: 214
Registriert: Fr 13. Apr 2018, 00:13

Hallo bibsi,

wenn Du Zahlen (Jahreszahl und Monatszahl) zu einem String verkettest, wird darauf die alphabetische Sortierung angewendet, nicht die numerische. Die Sortiermethode ist datentypabhängig. Alphabetisch sortiert kommt 10 vor 2. Du brauchst entweder lpad für den Monat, damit Einsteller eine 0 davor bekommen und alphabetisch richtig sortieren:

Code: Alles auswählen

select lpad(extract(month from berechnet_am), 2, '0') || '/' || extract(year from berechnet_am) zeitraum,
       extract(year from berechnet_am) || '.' || lpad(extract(month from berechnet_am), 2, '0') yyyymm,
       sum(summe_mappe)
from mappe
group by 1, 2
order by 2
oder Du sortierst direkt über die Zahlen:

Code: Alles auswählen

select lpad(extract(month from berechnet_am), 2, '0') || '/' || extract(year from berechnet_am) zeitraum,
       extract(year from berechnet_am) jahr,
       extract(month from berechnet_am) monat,
       sum(summe_mappe)
from mappe
group by 1, 2, 3
order by 2, 3
Zur besseren Lesbarkeit würde ich in beiden Fällen im angezeigten Zeitraum die Monate mit 0 auffüllen.

Übrigens: poste SQL-statements lieber als Text, Screenshots kann man weder inhaltlich suchen noch den Inhalt rauskopieren.

Viele Grüße, vr
Benutzeravatar
bibsi
Beiträge: 5
Registriert: Fr 23. Okt 2020, 10:29

:o Wauw, das ist die hohe Schule der SQL-Programierung.
lpad hatte ich noch nicht am Schirm. Da hab ich noch Nachholbedarf.

Super, läuft wies soll. Danke!
Übrigens: poste SQL-statements lieber als Text, Screenshots kann man weder inhaltlich suchen noch den Inhalt rauskopieren.
Habs geändert ;) Danke.
Antworten