[SQL] Trend uitrekenen?

Pagina: 1
Acties:

Acties:
  • 0 Henk 'm!

  • Dontwan
  • Registratie: Oktober 2012
  • Laatst online: 03-01-2024
Hallo allemaal,

Zelf ben ik "nog" geen superheld in SQL maar ik begin het steeds meer te leren. Echter kom ik er maar niet uit bij één query. Misschien dat jullie mij kunnen helpen.

Ik ben bezig met het maken van een grafiek in PHP met combinatie van een SQL database.
In deze grafiek wil ik elke week het gemiddelde weergeven met een trendlijn, het gemiddelde lukt me, echter kom ik er maar niet uit hoe je de trend kan berekenen in SQL.

Mijn tabel heet dbo.waardes_chart_data en ziet er als volgt uit:

WeeknummerTrendGemiddelde
11
21
32
45
51
etc. tot week 53

Het tabel zal er uiteindelijk als volgt uit moeten komen te zien:
WeeknummerTrendGemiddelde
111
211
31,332
42,255
521


Is er iemand die mij hiermee kan helpen?
Alvast bedankt! :)

Acties:
  • 0 Henk 'm!

  • Knutselsmurf
  • Registratie: December 2000
  • Laatst online: 10-10 18:08

Knutselsmurf

LED's make things better

Hoe zou je, zonder SQL, de trend uitrekenen? Als je die berekening weet, kun je stappen nemen om dat om te zetten naar een SQL-query

- This line is intentionally left blank -


Acties:
  • 0 Henk 'm!

  • Woy
  • Registratie: April 2000
  • Niet online

Woy

Moderator Devschuur®
In deze case lijkt het mij makkelijker om de trend pas aan de consumerende kant van de data met procedurele code op te lossen.

Het lijkt erop dat je nu gewoon alle voorgaande elementen sommeert, en deelt door het aantal elementen.

Als je het perse in SQL wilt doen zul je iets met een correlated sub-query moeten doen.

“Build a man a fire, and he'll be warm for a day. Set a man on fire, and he'll be warm for the rest of his life.”


Acties:
  • 0 Henk 'm!

  • Dontwan
  • Registratie: Oktober 2012
  • Laatst online: 03-01-2024
Knutselsmurf schreef op maandag 21 december 2015 @ 15:43:
Hoe zou je, zonder SQL, de trend uitrekenen? Als je die berekening weet, kun je stappen nemen om dat om te zetten naar een SQL-query
Zonder SQL zal ik de berekening zo uitvoeren:

Week 1: Gemiddelde van week 1 / 1
Week 2: (Gemiddelde van week 1 + Gemiddelde van week 2) / 2
Week 3: (Gemiddelde van week 1 + Gemiddelde van week 2 + Gemiddelde van week 3) / 3

etc.
Als ik dit omzet naar een query, dan ben ik 53 regels verder.. er moet een makkelijker manier zijn. :9~

Acties:
  • 0 Henk 'm!

  • Janoz
  • Registratie: Oktober 2000
  • Laatst online: 15:36

Janoz

Moderator Devschuur®

!litemod

Het lijkt me makkelijker om de trend gewoon in php te berekenen. Databases zijn goed in het opslaan en teruggeven van relationele data met daarbij mogelijk een stuk aggregatie. Een trend berekening is echter niet een aggregatie. Het is veel simpeler om die berekening te doen op het moment dat je je resultset aan het uitlezen bent. Dan is het slechts 1 of 2 regeltjes code ipv een onbegrijpelijke bak SQL.

Ken Thompson's famous line from V6 UNIX is equaly applicable to this post:
'You are not expected to understand this'


Acties:
  • 0 Henk 'm!

  • Rannasha
  • Registratie: Januari 2002
  • Laatst online: 11-10 20:26

Rannasha

Does not compute.

Ik zou dit overigens niet echt een trend willen noemen. Bij een trend denk ik eerder aan iets als een meebewegend gemiddelde (moving average). Dit is eerder een year-to-date waarde van het gemiddelde.

Verder ben ik het met Janoz eens dat dit waarschijnlijk makkelijker te doen is buiten de database om.

|| Vierkant voor Wiskunde ||


Acties:
  • 0 Henk 'm!

  • pedorus
  • Registratie: Januari 2008
  • Niet online
De antwoorden hierboven kloppen, maar mocht het perse in SQL moeten dan kan het met een zogenaamde self join. Iets als
SQL:
1
2
3
select a.weeknummer, avg(b.gemiddelde) as trend, a.gemiddelde from dbo.waardes_chart_data as a 
inner join dbo.waardes_chart_data as b on b.weeknummer <= a.weeknummer 
group by a.weeknummer, a.gemiddelde


", a.gemiddelde" op het einde kan weg als a.weeknummer een key is, afhankelijk van het dialect.

Vitamine D tekorten in Nederland | Dodelijk coronaforum gesloten


Acties:
  • 0 Henk 'm!

  • Gomez12
  • Registratie: Maart 2001
  • Laatst online: 17-10-2023
pedorus schreef op maandag 21 december 2015 @ 19:53:
De antwoorden hierboven kloppen, maar mocht het perse in SQL moeten dan kan het met een zogenaamde self join.
Hmm, altijd leuk om te zien hoe mensen het kunnen oplossen.

Maar ik zou zeggen werk hem eens voor 53 weken uit en het is redelijk evident waarom het afgeraden wordt.

Mocht het echt op de dbase server moeten gebeuren dan moet je alsnog geen sql gebruiken, maar simpelweg gaan kijken naar t-sql of het oracle/postgresql equivalent daarvan. Die zijn juist gemaakt voor dit soort dingen (loopjes over sql-code)

Acties:
  • 0 Henk 'm!

  • pedorus
  • Registratie: Januari 2008
  • Niet online
Als je een rolling average van 53 weken bedoelt dan wordt dat vervelend ja, als we data hebben over slechts 1 jaar dan werkt die query gewoon. Maar eigenlijk geeft het datamodel te denken als je er maar 1 jaar in kan opslaan (tenzij dit een view is, maar dat zal wel niet).

Ik kijk de OP net even door en zie dat er PHP genoemd wordt. Dit is dan natuurlijk de plek waarin het moet worden opgelost.

Als ik die query tegenkwam zou ik hem dus om twee redenen afwijzen ;)

Vitamine D tekorten in Nederland | Dodelijk coronaforum gesloten


Acties:
  • 0 Henk 'm!

  • jlrensen
  • Registratie: Oktober 2000
  • Laatst online: 23:48

jlrensen

plaatjes vullen geen gaatjes

Als je mssql 2012 of recenter gebruikt, kun je ook kijken naar de "lag" functie. Daarmee kun je een waarde uit het bovenliggende record halen. Dan sla je bij trend het totaal op, en deel je door het weeknummer in de query. De nieuwe totaalwaarde wordt dan je weekwaarde plus de totaalwaarde van het vorige record.

Men moet het denken bijbrengen, niet wat al gedacht is. ~C. Gurlitt


Acties:
  • 0 Henk 'm!

  • 4Real
  • Registratie: Juni 2001
  • Laatst online: 14-09-2024
Ik zou al geen gemiddelde opslaan, want je kunt nooit terug naar de individuele meetpunten. Daarnaast moet je jezelf de volgende vragen eens stellen: Hoe ga je om met trendanalyses over verschillende tijd-periodes? Of trendanalyses met meerdere dimensies (verkopen over x weken waarbij provincies y en z met elkaar worden vergeleken? Wat als je data een niet linieare trend volgt?

Acties:
  • 0 Henk 'm!

  • Croga
  • Registratie: Oktober 2001
  • Laatst online: 12-10 08:11

Croga

The Unreasonable Man

4Real schreef op vrijdag 25 december 2015 @ 09:18:
Ik zou al geen gemiddelde opslaan, want je kunt nooit terug naar de individuele meetpunten.
^^ dit.
Dit is geen vraagstuk voor een relationele database, dit is een BI vraagstuk. Zet er dan ook een bijbehorende BI database achter zodat je analyse tool met de juiste gegevens dit soort informatie kan ophoesten.

Acties:
  • 0 Henk 'm!

  • MSalters
  • Registratie: Juni 2001
  • Laatst online: 13-09 00:05
Gomez12 schreef op maandag 21 december 2015 @ 21:40:
[...]

Maar ik zou zeggen werk hem eens voor 53 weken uit en het is redelijk evident waarom het afgeraden wordt.
(52 × trend van vorige week + nieuwe waarde )/ 53. Simpel.

De echte truc is een week 0 invoegen met trend 0 zodat week 1 dezelfde formule kan gebruiken

Man hopes. Genius creates. Ralph Waldo Emerson
Never worry about theory as long as the machinery does what it's supposed to do. R. A. Heinlein


Acties:
  • 0 Henk 'm!

  • Morrar
  • Registratie: Juni 2002
  • Laatst online: 12-10 00:11
Waarom sla je niet iedere week ook het cumulatieve gemiddelde op? Dus bij week 2 het (cumulatieve) gemiddelde van week 1 + het gemiddelde van week 2. Bij week 3 het cumulatieve gemiddelde van week 2 + het gemiddelde van week 3. Enzovoorts. De tabel wordt dan:

WeeknummerGemiddeldeCum. Gemiddelde
111
212
324
459
5110


De trend kun je vervolgens heel simpel berekenen door het cumulatieve gemiddelde van een week te delen door het weeknummer. Die hoef je dus niet op te slaan:

SELECT cum_gemiddelde / weeknummer AS trend FROM table;

Overigens weet ik niet wat je met de trend zou willen; zou je niet een time frame erbij nemen zodat het een echt moving average wordt of wil je echt alle gemiddelden even zwaar laten meewegen?

En zo ja, is het niet beter om echt een linear model te fitten door alle gemiddelden? Bij veel data zou je in dat geval eens naar Spark kunnen kijken, kun je het in een cluster doen waardoor het lineair schaalt.

[ Voor 25% gewijzigd door Morrar op 26-12-2015 21:49 ]


Acties:
  • 0 Henk 'm!

  • Fiander
  • Registratie: Februari 2001
  • Laatst online: 28-05 12:35
Sorry dat ik nu pas reageer, maar het is vrijdag middag, en ik verveelde me en keek voor het eerst in maanden weer eens hier op het forum.

Geen idee ofdat je MSSQL2012 of nieuwe gebruikt, daar is nog geen antwoord op geweest, maar in dat geval heb je de beschikking over het OVER commando (windowed functie werd al eerder genoemt)

CREATE TABLE #T (Id INT, Gemmidelde FLOAT);
INSERT INTO #T ( Id, Gemmidelde ) VALUES ( 1,1),(2,1),(3,2),(4,5),(6,1);

SELECT
Id,
Gemmidelde,
AVG(Gemmidelde)
OVER (
ORDER BY Id
ROWS BETWEEN 53 PRECEDING AND CURRENT ROW
) AS Trend
FROM #T;

DROP TABLE #t;

Success, en sry voor het grafgraven en oprakelen oude topic

[ Voor 0% gewijzigd door Fiander op 19-02-2016 19:27 . Reden: typo ]

Deze sig is een manueel virus!! Als je dit leest heb je het. Mail dit bericht naar iedereen die je kent, en verwijder alle bestanden van je computer.

Pagina: 1