tellen in een database

Overzicht Reageren

Sponsored by: Vacatures door Monsterboard

Veur Heur

Veur Heur

04/05/2025 08:21:33
Quote Anchor link
Ik heb een database met (onder andere) de volgende tabellen:

- achtbanen: achtbaanid, inversies
- ritten: achtbaanid, ritten
- eigenschappen: achtbaanid, eigenschapid

(bovenstaande zijn de gesimplificeerde weergaves omdat niet alle kolommen van belang zijn voor mijn vraag)

Ik wil graag tellen hoeveel keer iemand over de kop is gegaan. Dit doe ik middels de volgende query:

Code (php)
PHP script in nieuw venster Selecteer het PHP script
1
SELECT SUM(achtbanen.inversies*ritten.ritten) AS total_number_of_inversions FROM achtbanen INNER JOIN ritten ON achtbanen.achtbaanid=ritten.achtbaanid WHERE achtbanen.inversies!=0


Echter: er zijn achtbanen die je eerst vooruit doet en daarna achteruit. Hierbij heb je dus 2x het aantal inversies (over de kop moment in een achtbaan). Voorheen had ik dit simpel opgelost door het aantal inversies bij een achtbaan x2 te doen, echter wil ik dit anders aanpakken.

In de tabel met eigenschappen staat o.a. eigenschapid 17 wat betekent dat een achtbaan een zogeheten "boomerang" is, met andere woorden: de achtbaan gaat eerst vooruit en daarna achteruit. Op basis van die eigenschap zou het mogelijk moeten zijn te bepalen wanneer het aantal inversies verdubbeld moet worden, toch?

Tips hoe de query er dan uit komt te zien?
 
PHP hulp

PHP hulp

16/05/2025 21:54:04
 
- Ariën  -
Beheerder

- Ariën -

04/05/2025 09:33:13
Quote Anchor link
Ik moest ook even nadenken, en ik heb even overleg gevoerd met AI, en daarbij kwam deze robuuste oplossing naar voren. In zulke gevallen als je randvoorwaarden heb (die in je PHP zou uitschrijven met if-else), zou een CASE in de query goed van pas komen.


Code (php)
PHP script in nieuw venster Selecteer het PHP script
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
SELECT SUM(
    ritten.ritten * achtbanen.inversies *
    (CASE
        WHEN EXISTS (
            SELECT 1
            FROM eigenschappen
            WHERE eigenschappen.achtbaanid = achtbanen.achtbaanid
            AND eigenschappen.eigenschapid = 17
        )
        THEN 2
        ELSE 1
    END)
) AS total_number_of_inversions
FROM achtbanen
INNER JOIN ritten ON achtbanen.achtbaanid = ritten.achtbaanid
WHERE achtbanen.inversies != 0


Het is het proberen waard.
 
Veur Heur

Veur Heur

04/05/2025 14:48:53
Quote Anchor link
Thanks, dat lijkt inderdaad het gewenste resultaat te geven. Moet het nog even doortesten, maar dit is een goede basis.
 
Ivo P

Ivo P

06/05/2025 10:53:56
Quote Anchor link
Ik hou er wel van om gebruik te maken van de eigenschappen van Mysql, dat maakt dat TRUE gelijk is aan 1 en FALSE aan 0.

Dus als het id 17 is dan geldt dat (eigenschapid = 17) gelijk is aan 1. Dat + 1 levert dan 2 op.
En als het niet voorkomt dan is die eigenschapid dus NULL. Dat is niet gelijk aan 17 en dus FALSE cq. 0.
0 + 1 levert 1 op voor de factor.

Dat maakt dat je niet in je formule opgescheept zit met 10 regels voor een CASE. En in dit geval vermijd ik ook nog een subquery, die in mijn ervaring vaak traag zijn.
Maar vooral dat laatste moet je wel even testen...

Code (php)
PHP script in nieuw venster Selecteer het PHP script
1
2
3
4
5
6
7
8
SELECT SUM(
    ritten.ritten * achtbanen.inversies *
      ((eigenschappen.eigenschapid = 17) + 1)
) AS total_number_of_inversions
FROM achtbanen
INNER JOIN ritten ON achtbanen.achtbaanid = ritten.achtbaanid
LEFT JOIN eigenschappen ON eigenschappen.achtbaanid = achtbanen.achtbaanid AND eigenschappen.eigenschapid = 17
WHERE achtbanen.inversies != 0
 
Veur Heur

Veur Heur

07/05/2025 10:00:27
Quote Anchor link
Dank voor je input Ivo, maar jouw versie lijkt juist alleen de boomerang achtbanen terug te geven.
 



Overzicht Reageren

 
 

Om de gebruiksvriendelijkheid van onze website en diensten te optimaliseren maken wij gebruik van cookies. Deze cookies gebruiken wij voor functionaliteiten, analytische gegevens en marketing doeleinden. U vindt meer informatie in onze privacy statement.