SQL query aanpassen lukt niet

Pagina: 1
Acties:

Onderwerpen

Vraag


  • DeRooney
  • Registratie: Oktober 2002
  • Laatst online: 17-07 20:07
Mijn vraag
Ik ben een tijdje geleden begonnen met wat basis SQL. Ik heb een proef/test database gedownload en alle benodigde software. Al spelende en online tutorial (W3) voor SQL volgend kwam bii mij iets in mijn hoofd dat ik graag wilde realiseren : 2 tabellen (of 3 zelfs) gejoind, en voor deze een groepering van namen van medewerkers op de eerste letter van de achternaam, met daarbij het aantal per letter, het totale bedrag aan salaris en het totaal aan omzet waar deze medewerkers voor zorgen.

Ik kwam er zelf al niet uit maar na een vraag op stackoverflow kreeg ik een werkende query. Althans, ik krijg een tabel. Maar niet gegroepeerd om de eerste letter van het alfabet:
SELECT A.[1e_Initiaal_Achternaam],
A.[Gem. Salaris],
A.[Salaris],
A.[Count],
(SELECT sum(orderbedrag)
FROM Orders WHERE WerknemerID = A.WerknemerID ) as [Order Waarde],
(SELECT sum(orderbedrag) / round(cast(A.Salaris as Int),0)
FROM Orders WHERE WerknemerID = A.WerknemerID ) as [AVG Salaris]
FROM (

SELECT WerknemerID,
Left(Achternaam, 1) as '1e_Initiaal_Achternaam',
cast(avg(Salaris) as Int) AS 'Gem. Salaris',
round(cast(sum(Salaris) as Int),0) as 'Salaris',
Count(Left(Achternaam, 1)) as 'Count'
FROM [dbo].[Werknemer]
GROUP BY Left(Achternaam, 1), WerknemerID
) AS A
ORDER BY A.[1e_Initiaal_Achternaam];

Ik heb naar de code gekeken om te kijken of ik het snap. Ik vermoed dat hij niet alles van de letter B bij elkaar optelt omdat hij ook nog moet groeperen op WerknemerID. En die is uniek per werknemer.
Als ik die uit de group By haal, werkt mijn query niet: dan krijg ik een foutmelding dat ik werknemerID niet gebruikt heb in een aggregate of een group by clause.

Ik heb er nu tijdje op zitten broeden maar ik kom er niet uit. Ik probeer de query te begrijpen zodat ik deze ook kan wijzigen, maar dat wil nog niet echt.

Kan iemand mij hier wegwijs in maken wellicht?

Afbeeldingslocatie: https://tweakers.net/i/p8J9Ff0nV4g8yEHqI4HruC3jdl4=/x800/filters:strip_exif()/f/image/U1iK8H0Ds0LkLF8DBuTiXnp5.png?f=fotoalbum_large

[ Voor 14% gewijzigd door DeRooney op 23-11-2023 14:48 . Reden: afbeeldingen toegevoegd. ]

Alle reacties


  • Paul!1987!
  • Registratie: April 2018
  • Laatst online: 19:54
Misschien werknederID zowel uit de group by als uit de select halen?

Acties:
  • +1 Henk 'm!

  • erwn
  • Registratie: November 2020
  • Niet online
Je haalt blijkbaar ook nog het orderBedrag op via de werknemerID, dus in deze opzet met een select * from (subquery) kun je die werknemerID nog niet weglaten in je subquery. Volgens mij kun je wel de twee queries combineren om in één keer de salaris-bedragen en order-bedragen op te halen gegroepeerd op initiaal.

  • Luit
  • Registratie: Februari 2001
  • Niet online
Dit is de basis:

code:
1
2
3
4
5
6
7
8
9
SELECT 
    LEFT(w.Achternaam, 1) as [1e_Initiaal_Achternaam]
    , CAST(AVG(w.Salaris) AS INT) AS [Gem. Salaris]
    , SUM(w.Salaris) AS [Salaris]
    , SUM(o.orderbedrag) AS [Order Waarde]
    , SUM(o.orderbedrag / CAST(A.Salaris as Int)) AS [AVG Salaris]
FROM [dbo].[Werknemer] w
LEFT JOIN [dbo].[Orders] o ON o.WerknemerID = w.WerknemerID
GROUP BY LEFT(w.Achternaam, 1)


Met deze simpele left join combineer je de werknemers met de bijbehorende orders, en groepeer je deze set op de eerste letter van de achternaam.

Vervolgens wil je weten hoeveel werknemers er zijn die een bepaalde beginletter van hun achternaam hebben. Hier zijn een aantal mogelijkheden voor:

- Met behulp van een window function. Deze regel stop je in de select:
code:
1
SUM(COUNT(w.Achternaam)) OVER(PARTITION BY LEFT(w.Achternaam, 1)) AS [Count]

- Met behulp van een nested query in je select:
code:
1
(SELECT COUNT(w2.Achternaam) FROM [dbo].[Werknemer] w2 WHERE LEFT(w2.Achternaam, 1) = LEFT(w.Achternaam, 1)) AS [Count]

- Of met behulp van een tweede join met de werknemers tabel