Stel in de database staat een aantal records met in elk een andere begin- en een eindtijd (verder nog veel meer info).

BIJV:
drie tijdranges begintijd-eindtijd op datum1
twee tijdranges begintijd-eindtijd op datum2
een tijdrange begintijd-eindtijd op datum3

datum1: 09:00-11:30 13:00-15:00 20:00-22:30
datum2: 09:00-11:30 20:00-22:30
datum3: 13:00-15:00

Ik wil nu bijv een record met daarin 13:00-15:00 toevoegen op deze drie datums als dat kan, anders niet.
Op datum1 en datum3 gaat dat niet (bezet), maar wel op datum2 (range is nog vrij).

datum2 moet dus worden:
datum2: 09:00-11:30 13:00-15:00 20:00-22:30
de andere datums blijven ongewijzigd,

Hoe kan ik dit makkelijk doen?

Ik heb geprobeerd in een while steeds een record te lezen dan te bepalen of het record met de nieuwe range past, maar kan dat niet bepalen. Ik heb geprobeerd eerst alle records van eenzelfde datum te lezen en die in een variabele zetten en dan te bepalen of het nieuwe record met de gegeven tijdrange past, maar kom daar als beginner niet uit.

Wie kan helpen?

Bvd
Waarom moet je alle records van 1 dag tegelijk hebben? Waarom een while-loop?

Volgens mij kan het in 1 query, waarbij je controleert of voor de betreffende datum de begintijd valt tussen een reeds bestaand aanvangmoment en eindmoment en controleert of er de eindtijd valt tussen een reeds bestaand aanvangmoment en eindmoment. de WHERE krijgt dus meerdere voorwaarden om te controleren.
Als je resultaat 0 rijen oplevert, zit je volgens mij goed.

Hoe vraag je nu de gegevens op/controleer je?

Let op, gesorteerd op oplopende datum en daarbinnen op oplopende tijd:
Hoe het in de database staat, op welke volgorde, is totaal niet van belang. Al staan er 10.000 periodes in, helemaal door elkaar, maakt voor de database niks uit.

omdat je dan eigenlijk alle records van één dag tegelijk moet hebben om te bekijken.
Sterker nog; niet alleen van die dag, maar van alle dagen. Een periode kan namelijk ook van 23:00 tot 01:00 uur zijn en dan is het eindmoment dus niet op dezelfde dag als het beginmoment.

Bij elke doorgang van de while-loop wordt er steeds één record gelezen en is de vorige weer weg.
Welke while-loop?


<?php
// je db connectie
$mysqli = mysqli_connect($host,$user,$pass,$dbas) or die("Fout: ".mysqli_error($mysqli));

// deze gegevens komen uiteindelijk uit een formulier waarschijnlijk, nu even zo
$aanvang = '2014-08-22 14:10:00';
$einde = '2014-08-22 14:20:00';
	
$controle = $mysqli->query("
				SELECT
					periode_ID
				FROM
					periodes
				WHERE
					aanvangsmoment BETWEEN '".mysqli_real_escape_string($mysqli,$aanvang)."' AND '".mysqli_real_escape_string($mysqli,$einde)."'
					OR eindmoment BETWEEN '".mysqli_real_escape_string($mysqli,$aanvang)."' AND '".mysqli_real_escape_string($mysqli,$einde)."'
				");
								
if(mysqli_num_rows($controle)) == 0){
echo 'periode is nog vrij dus lekker invoeren!';
}
else{
echo 'periode niet vrij!';
}
?>
@Ramon: in zijn database staat datum in een ander veld dan aanvang- / eindtijd (zie post Andre Janssen 22/08/2014 14:51:11).
Dat klopt.

En alle tijden bij elkaar gemoffeld in 1 record als string.
Dat heb ik dus al aangegeven dat het dan nooit gaat werken en het alleen werkt als zijn database tabel op een andere manier ingericht is.
Hoi Ramon,
1. Eigenlijk is jouw oplossing ook een (verkapte) loop, maar dan over de hele tabel 'periodes'.
2. Een periode kan in mijn geval alleen op een één datum vallen, de dag eindigt om 12 uur 's nachts.
Een periode loopt dus niet over naar de volgende dag.
3. De datum staat in een apart veld. Maar dat is niet zo'n probleem denk ik.
4. Het feit dat de te plaatsen periode niet past binnen een van de reeds aanwezigen wil niet zeggen dat die daarbuiten dus wél past.

Ik heb het idee dat jouw oplossing zer zeker in de goede richting wijst. Als beginner schrijf ik eea nog niet zo compact als jij maar gebruik ik meer statements.

Feit is volgens mij wel dat jij de hele database afzoekt, terwijl ik alleen de records van een bepaalde datum check hetgeen natuurlijk sneller gaat, lijkt me. De datum moet dus op een of andere manier in de query worden verwerkt?
Misschein is dat wat 'Obelix en Idefix' bedoelt?

mvg

Andre Janssen op 22/08/2014 16:11:17

3. De datum staat in een apart veld. Maar dat is niet zo'n probleem denk ik.


Waarom?
Dat is alleen maar onhandig.
Ramon,
Nee, "alle tijden bij elkaar gemoffeld in 1 record als string": dat is niet zo.
datum, aanvangstijd en eindtijd zijn aparte velden!
In jouw scriptje zou ik de datum er bijv. gewoon bij kunnen zetten.
Maar blijft de wens om niet de hele tabel te moeten doorspitten, immers de records zijn al gesortreerd op datum en daarbinnen op tijd (zie eerdere reacties).

mvg
Andre Janssen op 22/08/2014 16:11:17

Hoi Ramon,
1. Eigenlijk is jouw oplossing ook een (verkapte) loop, maar dan over de hele tabel 'periodes'.

Hoezo een loop?

Andre Janssen op 22/08/2014 16:11:17

3. De datum staat in een apart veld. Maar dat is niet zo'n probleem denk ik.

Daarmee maak je het jezelf lastiger. Maar als dat geen probleem is.... ;-)

Andre Janssen op 22/08/2014 16:11:17

4. Het feit dat de te plaatsen periode niet past binnen een van de reeds aanwezigen wil niet zeggen dat die daarbuiten dus wél past.

Die moet je me even uitleggen. Waarom zou die niet passen?

Andre Janssen op 22/08/2014 16:11:17

Als beginner schrijf ik eea nog niet zo compact als jij maar gebruik ik meer statements.

Weet niet hoe je veel meer statements nodig hebt, maar laat eens zien wat je hebt.

Andre Janssen op 22/08/2014 16:11:17
Feit is volgens mij wel dat jij de hele database afzoekt, terwijl ik alleen de records van een bepaalde datum check
hetgeen natuurlijk sneller gaat, lijkt me.

En die records staat toch in dezelfde database als de database die Ramon doorzoekt?
Alleen ga jij op drie velden zoeken (datum, aanvang, eind) en Ramon op twee velden. Mag jij raden wat sneller is.... ;-)


Andre Janssen op 22/08/2014 16:22:01

Maar blijft de wens om niet de hele tabel te moeten doorspitten, immers de records zijn al gesortreerd op datum en daarbinnen op tijd (zie eerdere reacties).

Volgens mij maak je een denkfout. Een database is er, mits goed opgezet, voor bedoeld om heeeeeeel veeeeel informatie te bevatten en die heel snel te tonen, zodra er om gevraagd wordt. Een database zal per definitie helemaal doorlopen moeten worden om alle resultaten te tonen. Of je de manier van Ramon gebruikt of jouw manier.
Verder is het niet mogelijk om een record toe te voegen tussen bestaande records. Een nieuw record wordt (automatisch) toegevoegd aan het einde van een tabel.
Records en tijden zijn dus niet gesorteerd.
Geen idee waar jij dat idee vandaan haalt.
Maar met een goede database-opzet, maakt de volgorde ook niet uit.


3: De datum staat in een apart veld. Maar dat is niet zo'n probleem denk ik.
Immers in Ramon's scriptje kan ik de betreffende datum toch gewoon in $aanvang en $einde vooraan toevoegen?

4: Het feit dat de te plaatsen periode niet past binnen een van de reeds aanwezigen wil niet zeggen dat die daarbuiten dus wél past.
Het gaat er niet om om een vrije range te vinden maar om exact op dezelfde (vrije?) range te kunnen plaatsen.

5: Feit is volgens mij wel dat jij de hele database afzoekt, terwijl ik alleen de records van een bepaalde datum check hetgeen natuurlijk sneller gaat, lijkt me.
Ik kijk toch alleen maar in de records van eenzelfde datum, in dit geval twee op '2014-08-22'.
Immers mijn query sorteert de records op datum en daarabinnen op tijd.
Natuurlijk wordt een record ge-INSERT maar ik kan ze daarna SORTeren waarop ik wil, in dit geval op datum en daarbinnen op tijd. Daarna kan het in het resultaat van de query het ingevoerde record ahw 'ertussen' staan op dezelfde datum en een andere tijdrange. Het is maar hoe je het bekijkt denk ik.

In elk geval fijn dat jullie zo snel reageren en ik denk dat het scriptje zeer bruikbaar is.

mvg



[size=xsmall]Toevoeging op 22/08/2014 16:56:06:[/size]

mijn query ziet er alsvolgt uit:

rsv_sesdat is de sessiedatum
rsv_tot is de eindtijd
De rest zal wel duidelijk zijn hoop ik.

$query = ('SELECT * FROM ' . "$rsv_tabel" . " WHERE (rsv_sesdat = '$extrajjjjmmdd') ORDER BY rsv_sesdat ASC, rsv_tot ASC" );

mvg
Sorry Andre, ik geef het dan op met je te helpen.

Hele database afzoeken; voor database een fluitje van een cent
Periode kan maar op één datum zijn; maakt met mijn script niet uit
Datum en tijden apart opslaan: de problemen ondervind je nu al en worden alleen maar erger.

Maar je moet het zelf weten.

Reageren