Ich versuche, eine bestimmte Spalte über einen bestimmten Zeitraum zu summieren. Der Kicker ist, dass ich möchte, dass dies ein CTE ist, weil ich es mehrmals als Teil einer größeren Abfrage verwenden muss. Da es ein CTE ist, muss es die Datumsspalte sowie die Summen- und ID-Spalten haben, was bedeutet, dass ich nach Datum UND ID gruppieren muss. Das führt dazu, dass meine Ergebnisse nach ID und Datum gruppiert werden, sodass mir keine einzige Summe über den Zeitraum zur Verfügung steht, sondern eine Menge an Summen, eine für jeden Tag.Summieren einer Spalte über einen Datumsbereich in einem CTE?
es einfach zu machen, sagen wir:
create table orders (
id int primary key,
itemID int foreign key references items.id,
datePlaced datetime,
salesRep int foreign key references salesReps.id,
price int,
amountShipped int);
Jetzt haben wir das Gesamtgeld eine bestimmte Vertriebsmitarbeiter, die während eines Geschäftsjahres, aufgeschlüsselt nach Artikel erhalten möchten. Das heißt, das Geschäftsjahrjahr ignorierend:
select itemName, sum(price) as totalSales, sum(totalShipped) as totalShipped
from orders
join items on items.id = orders.itemID
where orders.salesRep = '1234'
group by itemName
Einfach genug. Aber wenn Sie noch etwas hinzufügen, sogar den Preis, spuckt die Abfrage viel mehr Zeilen aus, als Sie wollten.
select itemName, price, sum(price) as totalSales, sum(totalShipped) as totalShipped
from orders
join items on items.id = orders.itemID
where orders.salesRep = '1234'
group by itemName, price
Jetzt ist jede Gruppe (Name, Preis) statt nur (Name). Dies ist eine Art von Sudocode, aber in meiner Datenbank bewirkt nur diese Änderung, dass meine Ergebnismenge von 13 auf 32 Zeilen springt. Hinzu kommt, dass der Datumsbereich, und Sie wirklich ein Problem haben:
select itemName, price, sum(price) as totalSales, sum(totalShipped) as totalShipped
from orders
join items on items.id = orders.itemID
where orders.salesRep = '1234'
and orderDate between 150101 and 151231
group by itemName, price
Dieses auf das letzte Beispiel identisch ist. Das Problem ist, so dass es ein CTE:
with totals as (
select itemName, price, sum(price) as totalSales, sum(totalShipped) as totalShipped, orderDate as startDate, orderDate as endDate
from orders
join items on items.id = orders.itemID
where orders.salesRep = '1234'
and orderDate between startDate and endDate
group by itemName, price, startDate, endDate
)
select totals_2015.itemName as itemName_2015, totals_2015.price as price_2015, ...
totals_2016.itemName as itemName_2016, ...
from (
select * from totals
where startDate = 150101 and endDate = 151231
) totals_2015
join (
select *
from totals
where startDate = 160101 and endDate = 160412
) totals_2016
on totals_2015.itemName = totals_2016.itemName
Nun ist die Gruppierung in der CTE ist, ist unter mehr als das Hinzufügen der Preis es geschafft. Ich habe darüber nachgedacht, die Preisanfrage innerhalb des CTE in eine eigene Unterabfrage zu zerlegen, aber ich kann mir nicht entgehen lassen, nach den Daten gruppieren zu müssen, um den Datumsbereich zu erhalten. Kann jemand einen Weg da rum sehen? Ich hoffe, ich habe die Dinge klar genug gemacht. Dies wird auf einem IBM iSeries-Computer ausgeführt. Vielen Dank!
Warum denkst du 'Da es ein CTE ist, muss es die Datumsspalte haben 'ist wahr? –
Sorry, das habe ich nicht klargestellt. Der CTE wird verwendet, um mehrere Jahre zu erhalten, wie im letzten Beispiel. Auf diese Weise kann das gleiche CTE verwendet werden, um zwei, drei, vier oder mehr Jahre zu erhalten, indem einfach unterschiedliche Daten angegeben werden. Dies wird an eine Tabelle auf einer Website ausgegeben, mit einer Zeile pro Elementname und so vielen Spalten wie Jahren, multipliziert mit der Anzahl von (Preis, Gesamtversand, Gesamtumsatz). – AH16
Vielleicht ist eine temporäre Tabelle oder Sichtweise ein besserer Ansatz als eine CTE. Übrigens erhalten Sie eher Hilfe, wenn Sie sich die Mühe machen, Ihre Frage richtig zu formatieren, dh Ihren Code als Code zu formatieren. –