[PHP/MySQL] Parsetime van 3 seconden normaal?

Pagina: 1
Acties:

Onderwerpen


Acties:
  • 0 Henk 'm!

  • Ras
  • Registratie: December 2004
  • Niet online
Voor het bedrijfje van mijn ouders heb ik een php/mysql-systeempje gemaakt waar ze klanten in kunnen voeren en aan kunnen geven wat die klanten huren. Alle producten die te huur zijn komen in een tabel te staan waarin te zien is of een product nog beschikbaar is op een bepaalde datum.

zie screenshot:
Afbeeldingslocatie: http://raswebdesign.nl/beschikbaarheids-tabel.jpg

Deze pagina bestond eerst uit een php loop waarin circa 2000 queries aangeroepen werden. De pagina deed er 4 tot 4,5 seconden over om te parsen. Ik veronderstelde dat dit nogal lang is en besloot de code te herschrijven.

De 2000 queries teruggebracht tot 1 enkele query die zijn gegevens uit 3 verschillende databasetabellen haalt. PHP code er bij geschreven en de nieuwe parsetime is: 2,5 à 3 seconden! Goed nieuws, het is minder geworden, maar is dit normaal voor een dergelijke pagina of moet ik eens met de host gaan praten? Er staan circa 70 producten in de lijst.

Antec Fusion Black, Intel e8400, EAH3450 512MB, 2x2GB pc6400 kingston, p5e-vm hdmi, 1x1TB 1x500GB


Acties:
  • 0 Henk 'm!

  • b19a
  • Registratie: September 2002
  • Niet online
Haal je code eens door een profiler (bv. xdebug) en kijk waar de meeste tijd in gaat zitten. Mogelijk leun je nu teveel op code om je data te verzamelen. Probeer een evenwicht tussen code en database te vinden.

Allicht kun je wat (pseudo-)code posten om ons mee te laten denken.

Acties:
  • 0 Henk 'm!

  • HuHu
  • Registratie: Maart 2005
  • Niet online
Hoe lang doet je query er zelf over? Dus alleen de query, zonder de PHP code die er omheen zit. Dan kun je al snel zien of je de query moet optimaliseren, of dat er iets geks gebeurd in PHP.

Acties:
  • 0 Henk 'm!

  • Juup
  • Registratie: Februari 2000
  • Niet online
Een paar rake indices op de database kunnen soms veel schelen.

Een wappie is iemand die gevallen is voor de (jarenlange) Russische desinformatiecampagnes.
Wantrouwen en confirmation bias doen de rest.


Acties:
  • 0 Henk 'm!

  • Ras
  • Registratie: December 2004
  • Niet online
Ik heb even gechecked hoe lang de query er zelf over doet: 0.08916 secs.

Antec Fusion Black, Intel e8400, EAH3450 512MB, 2x2GB pc6400 kingston, p5e-vm hdmi, 1x1TB 1x500GB


Acties:
  • 0 Henk 'm!

  • HuHu
  • Registratie: Maart 2005
  • Niet online
Ras schreef op vrijdag 13 maart 2009 @ 18:55:
Ik heb even gechecked hoe lang de query er zelf over doet: 0.08916 secs.
Is dat zonder caching?

Acties:
  • 0 Henk 'm!

  • Janoz
  • Registratie: Oktober 2000
  • Laatst online: 02:21

Janoz

Moderator Devschuur®

!litemod

Zonder een stukje query, database model en/of code is er natuurlijk 0 komma nada te zeggen over waar de oorzaak van de vertraging ligt.

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!

  • ACM
  • Registratie: Januari 2000
  • Niet online

ACM

Software Architect

Werkt hier

(jarig!)
Janoz schreef op vrijdag 13 maart 2009 @ 19:13:
Zonder een stukje query, database model en/of code is er natuurlijk 0 komma nada te zeggen over waar de oorzaak van de vertraging ligt.
Inderdaad, maar desalniettemin is het vermoeden van Ras dat 2 seconde nog steeds veel is voor een pagina we juist. Gebruikers willen liefst niet hoeven te wachten.

Met wat tactisch plaatsen van microtime-calls kan je overigens ook al een hoop "profiling" informatie achterhalen, zonder gelijk moeilijk te moeten doen met ondersteuning voor profilers (zeker als je van een hoster afhankelijk bent nogal onhandig) die bovendien zelf ook weer vertraging introduceren.

Acties:
  • 0 Henk 'm!

  • Ras
  • Registratie: December 2004
  • Niet online
@Huhu: Ja, zonder caching. Het is ook niet zo dat een parsetime van 3 seconden vervelend is voor het huidige gebruik. Er maken slechts 3 personen gebruik van die samen niet vaker dan 30 keer op een dag die pagina tevoorschijn toveren. Ik ben echter wel benieuwd of het efficiënter behoord te zijn, zodat ik er van kan leren.
Janoz schreef op vrijdag 13 maart 2009 @ 19:13:
Zonder een stukje query, database model en/of code is er natuurlijk 0 komma nada te zeggen over waar de oorzaak van de vertraging ligt.
Dat ben ik met je eens en ik zal dan ook spoedig wat meer info daarover geven. Maar zoals de poster na je al had aangegeven was mijn vraag voornamelijk of de parsetime van 3 seconden normaal is.

De conclusie die ik nu trek uit de reacties is dat 3 seconden te veel is voor mijn pagina en dat het probleem niet bij de host en niet bij de query gezocht moet worden, maar bij de php code.

Ik ben inmiddels wel benieuwd hoe ik mijn code kan verbeteren en zal dan ook wel wat code gaan posten. Alvast bedankt voor jullie reacties! Nu eerst ff eten :)

[ Voor 17% gewijzigd door Ras op 13-03-2009 19:38 ]

Antec Fusion Black, Intel e8400, EAH3450 512MB, 2x2GB pc6400 kingston, p5e-vm hdmi, 1x1TB 1x500GB


Acties:
  • 0 Henk 'm!

  • Zoijar
  • Registratie: September 2001
  • Niet online

Zoijar

Because he doesn't row...

3 seconden is erg veel ja; brakke code en/of query.

[ Voor 32% gewijzigd door Zoijar op 13-03-2009 21:33 ]


Acties:
  • 0 Henk 'm!

  • Bart Brinkman
  • Registratie: Maart 2009
  • Laatst online: 20-10-2021
Zoijar schreef op vrijdag 13 maart 2009 @ 21:33:
3 seconden is erg veel ja; brakke code en/of query.
Of het gebrek aan een goede index...

Acties:
  • 0 Henk 'm!

  • FireDrunk
  • Registratie: November 2002
  • Laatst online: 20-09 11:06
ik zou iig even een timestamp uit laten printen voor en na je query... dan kan je iig kijken waar de meeste tijd in gaat zitten...
Want een for loopje over 2000 items en dan nog een for loopje doen op welk vakje kan bijvoorbeeld ook al gauw 2 seconden opleveren...

Even niets...


Acties:
  • 0 Henk 'm!

  • danslo
  • Registratie: Januari 2003
  • Laatst online: 14:07
Bart Brinkman schreef op vrijdag 13 maart 2009 @ 21:41:
[...]


Of het gebrek aan een goede index...
Dat is het dus niet, gezien deze post:
Ras in "\[PHP/MySQL] Parsetime van 3 seconden nor..."

Relevante stukken PHP posten dus.

Acties:
  • 0 Henk 'm!

  • Ras
  • Registratie: December 2004
  • Niet online
Ok, niet meer nodig om te raden wat de parsetime zo slecht maakt. Hier is het stuk code wat er 2 à 2,5 seconden over doet om te parsen:

PHP:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
<?
//Alle producten langslopen en een rij van weergeven
$p = 0; // variabele om om de 15 rijen de dagen vd week aan te geven
for($i = 0; $i < $num_rows; $i++){
    if($i == 0 OR $product_id[$i] != $product_id[$i-1]){
        
        // rij met dagen vd week neerzetten na iedere 15 regels
        if($p == 16){$p = 0; echo $maandrow;}
        $p++;
        
        echo("
            <tr>
                <td width=\"30\">$code[$i]</td>
                <td width=\"150\">$naam[$i]</td>
        ");
        //Alle dagen van de week weergeven voor product[i]
        $j = $i;
        for($k = 1; $k < $dagen_in_maand; $k++){                        //loop alle dagen langs voor product i
            $weekdag = date ("w", mktime (0,0,0,$maand,$k,date("Y")));  //welke dag van de week is het (ivm achtergrondkleurtje)?
            $datum_a = mktime(0,0,0,$maand,$k,date("Y"));               //begin van de dag
            $datum_b = mktime(0,0,0,$maand,$k+1,date("Y"));             //einde van de dag

            if(($datum_a <= $van[$j] AND $van[$j] <= $datum_b)
            OR ($datum_a <= $tot[$j] AND $tot[$j] <= $datum_b)
            OR ($van[$j] <= $datum_a AND $tot[$j] >= $datum_b)){
                echo("<td class=\"beschikbaarheid_1\">&nbsp;</td>"); //rood, oftewel niet beschikbaar
                if($tot[$j] < $datum_b AND $product_id[$j] == $product_id[$j+1]){$j++;}
            } else {
                if($k == date("d") and $maand == date("m")){    //huidige dag accentueren
                    echo("<td class=\"beschikbaarheid_vandaag\">&nbsp;</td>");
                } elseif($weekdag == 6 or $weekdag == 0){       //weekend accentueren
                    echo("<td class=\"beschikbaarheid_0b\">&nbsp;</td>");
                } else {
                    echo("<td class=\"beschikbaarheid_0\">&nbsp;</td>"); //wit
                }
            }
        }
        echo("
            </tr>
        ");
    }
}
?>


Om mijn code nog wat beter te begrijpen:

Uit de query haalt ie een aantal arrays:
- $van[$i] (huur vanaf deze datum)
- $tot[$i] (huur tot deze datum)
- $product_id[$i] (dûh)
- $code[$i] (productcode)
- $naam[$i] (productnaam)

Elk product komt tenminste 1 keer voor in de tabel die de query genereerd. Wanneer een product vaker in een maand word verhuurd komt ie 1x voor, per keer dat het verhuurd word.

Brand los.

[ Voor 9% gewijzigd door Ras op 13-03-2009 22:00 ]

Antec Fusion Black, Intel e8400, EAH3450 512MB, 2x2GB pc6400 kingston, p5e-vm hdmi, 1x1TB 1x500GB


Acties:
  • 0 Henk 'm!

  • FireDrunk
  • Registratie: November 2002
  • Laatst online: 20-09 11:06
for loop in for loop, en daarin mktime... dat duurt wel even ja :)

die $p kun je eruit slopen door " if ($i % 15 == 0)" te gebruiken...

misschien een raar id, maar kan je niet beter eerst het veld maken in een array, daarna pas uit je db alles in 1 keer ophalen, en in 1 for loop op de goede plek in de array het vakje verkleuren... dus bijvoorbeeld:

code:
1
2
3
4
5
6
7
8
9
10
Boolean[][] gebruik = new Boolean[aantalproducten][31(aantaldagen)];

$meuk = query();

for ($bezetting in $result)
{
gebruik[productid][$bezetting->datum] = true;
}

printArray();


Mocht je het per dag willen specificeren...

code:
1
2
3
4
5
6
7
8
9
10
Boolean[][] gebruik = new Boolean[aantalproducten][31(aantaldagen)][dagdelen];

$meuk = query();

for ($bezetting in $result)
{
gebruik[productid][$bezetting->datum][$bezetting->dagdeel] = true;
}

printArray();

[ Voor 115% gewijzigd door FireDrunk op 13-03-2009 22:07 ]

Even niets...


Acties:
  • 0 Henk 'm!

  • GlowMouse
  • Registratie: November 2002
  • Niet online
Grote kans dat je HTML-output erg groot is, en dat PHP op een bepaald moment wacht met de verdere uitvoering van je script totdat de client de output tot dan toe heeft ontvangen. Wat gebeurt er als je dezelfde pagina met wget vanaf de server zelf opvraagt?
thijs_cramer schreef op vrijdag 13 maart 2009 @ 21:58:
for loop in for loop, en daarin mktime... dat duurt wel even ja :)
We hebben het over 4000 calls naar mktime, dat duurt echt niet zolang.duurt wel vrij lang dus (1.2s op een Sempron 2800+). De cachingoplossing van $datum_a en $datum_b zoals MeAngry (onder) voorstelt, zou dus al veel uitmaken.

[ Voor 46% gewijzigd door GlowMouse op 13-03-2009 22:22 ]


Acties:
  • 0 Henk 'm!

  • --MeAngry--
  • Registratie: September 2002
  • Laatst online: 19-09 16:35

--MeAngry--

aka Qonstrukt

Als het echt de PHP executie is die zo lang duurt, zou ik eens proberen om $weekdag, $datum_a en $datum_b vantevoren eenmalig uit te rekenen, in array's stoppen, en vervolgens alleen nog maar even ophalen per product.
Je bent nu voor X producten, X aantal keren hetzelfde aan het doen. :)

Het probleem zou dan wel echt in mktime() moeten zitten, want ik zie verder geen erg gekke dingen. Heb je het geheel al eens lokaal proberen te testen? Wat doet het daar? Want misschien word je wel gigantisch belemmerd door de host die gewoon teveel users op 1 bak draait.

[ Voor 32% gewijzigd door --MeAngry-- op 13-03-2009 22:12 ]

Tesla Model Y RWD (2024)


Acties:
  • 0 Henk 'm!

  • FireDrunk
  • Registratie: November 2002
  • Laatst online: 20-09 11:06
--MeAngry-- schreef op vrijdag 13 maart 2009 @ 22:10:
Als het echt de PHP executie is die zo lang duurt, zou ik eens proberen om $weekdag, $datum_a en $datum_b vantevoren eenmalig uit te rekenen, in array's stoppen, en vervolgens alleen nog maar even ophalen per product.
Je bent nu voor X producten, X aantal keren hetzelfde aan het doen. :)

Het probleem zou dan wel echt in mktime() moeten zitten, want ik zie verder geen erg gekke dingen. Heb je het geheel al eens lokaal proberen te testen? Wat doet het daar? Want misschien word je wel gigantisch belemmerd door de host die gewoon teveel users op 1 bak draait.
offtopic:
^^ Wat hij zegt :P ^^

Even niets...


Acties:
  • 0 Henk 'm!

  • GlowMouse
  • Registratie: November 2002
  • Niet online
Ras schreef op vrijdag 13 maart 2009 @ 18:55:
Ik heb even gechecked hoe lang de query er zelf over doet: 0.08916 secs.
Query + explain output?

Acties:
  • 0 Henk 'm!

  • Ras
  • Registratie: December 2004
  • Niet online
De winnende oplossing :)
--MeAngry-- schreef op vrijdag 13 maart 2009 @ 22:10:
Als het echt de PHP executie is die zo lang duurt, zou ik eens proberen om $weekdag, $datum_a en $datum_b vantevoren eenmalig uit te rekenen, in array's stoppen, en vervolgens alleen nog maar even ophalen per product.
Je bent nu voor X producten, X aantal keren hetzelfde aan het doen. :)

Het probleem zou dan wel echt in mktime() moeten zitten, want ik zie verder geen erg gekke dingen. Heb je het geheel al eens lokaal proberen te testen? Wat doet het daar? Want misschien word je wel gigantisch belemmerd door de host die gewoon teveel users op 1 bak draait.
Het onderstaande stuk code doet er nog slechts een halve seconde over om te parsen. Een verbetering van 2 seconden dus.

PHP:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
<?
for($k = 1; $k < $dagen_in_maand; $k++){                            //loop alle dagen langs voor product i
    $weekdag[$k] = date ("w", mktime (0,0,0,$maand,$k,date("Y")));  //welke dag van de week is het (ivm achtergrondkleurtje)?
    $datum_a[$k] = mktime(0,0,0,$maand,$k,date("Y"));               //begin van de dag
    $datum_b[$k] = mktime(0,0,0,$maand,$k+1,date("Y"));
}

//Alle producten langslopen en een rij van weergeven
$p = 0; // variabele om om de 15 rijen de dagen vd week aan te geven
for($i = 0; $i < $num_rows; $i++){
    if($i == 0 OR $product_id[$i] != $product_id[$i-1]){
        
        // rij met dagen vd week neerzetten na iedere 15 regels
        if($p == 16){$p = 0; echo $maandrow;}
        $p++;
        
        echo("
            <tr>
                <td width=\"30\">$code[$i]</td>
                <td width=\"150\">$naam[$i]</td>
        ");
        //Alle dagen van de week weergeven voor product[i]
        $j = $i;
        for($k = 1; $k < $dagen_in_maand; $k++){                        //loop alle dagen langs voor product i
            if(($datum_a[$k] <= $van[$j] AND $van[$j] <= $datum_b[$k])
            OR ($datum_a[$k] <= $tot[$j] AND $tot[$j] <= $datum_b[$k])
            OR ($van[$j] <= $datum_a[$k] AND $tot[$j] >= $datum_b[$k])){
                echo("<td class=\"beschikbaarheid_1\">&nbsp;</td>"); //rood, oftewel niet beschikbaar
                if($tot[$j] < $datum_b[$k] AND $product_id[$j] == $product_id[$j+1]){$j++;}
            } else {
                if($k == date("d") and $maand == date("m")){    //huidige dag accentueren
                    echo("<td class=\"beschikbaarheid_vandaag\">&nbsp;</td>");
                } elseif($weekdag[$k] == 6 or $weekdag[$k] == 0){       //weekend accentueren
                    echo("<td class=\"beschikbaarheid_0b\">&nbsp;</td>");
                } else {
                    echo("<td class=\"beschikbaarheid_0\">&nbsp;</td>"); //wit
                }
            }
        }
        echo("
            </tr>
        ");
    }
}
?>

Hele pagina geladen in 0.55985 secs.
thijs_cramer schreef op vrijdag 13 maart 2009 @ 21:58:
die $p kun je eruit slopen door " if ($i % 15 == 0)" te gebruiken...
Bedankt voor de tip, maar dat kan niet. $i staat niet altijd gelijk aan een nieuwe regel.

Edit: Door het inzicht dat mktime() nogal wat tijd kost als het 2000 keer word aangeroepen op een pagina, heb ik mij bedacht dat dit bij date() ook wel eens het geval zou kunnen zijn. Daarom heb ik date("m") en date("d") ook maar eens in een variabele gestopt voor de loops. Dit resulteerde erin dat de parsetime van de gehele pagina is teruggebracht van 0,55 sec naar 0,25 sec.

[ Voor 10% gewijzigd door Ras op 13-03-2009 22:46 ]

Antec Fusion Black, Intel e8400, EAH3450 512MB, 2x2GB pc6400 kingston, p5e-vm hdmi, 1x1TB 1x500GB


Acties:
  • 0 Henk 'm!

  • WouZz
  • Registratie: Mei 2000
  • Niet online

WouZz

Elvis is alive!

Ook weer wat geleerd. PS: doe die date("Y") dan ook nog ff ;)

On track


Acties:
  • 0 Henk 'm!

Verwijderd

Ik denk ook even mee, misschien kan de parsetijd nog omlaag.
Wat is hier uitgekomen?
Tevens gaat hij dit
PHP:
1
if($i == 0 OR $product_id[$i] != $product_id[$i-1]){

net zoveel keer doen als er rows uit de query komen. Ik denk dat daar nog snelheidswinst te behalen is.

Acties:
  • 0 Henk 'm!

  • Woy
  • Registratie: April 2000
  • Niet online

Woy

Moderator Devschuur®
Ras schreef op vrijdag 13 maart 2009 @ 22:30:
Het onderstaande stuk code doet er nog slechts een halve seconde over om te parsen. Een verbetering van 2 seconden dus.
offtopic:
Ik denk dat je het over execution time hebt, het parsen van het script zal waarschijnlijk niet zo lang duren.

“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!

  • NMe
  • Registratie: Februari 2004
  • Laatst online: 09-09 13:58

NMe

Quia Ego Sic Dico.

Verwijderd schreef op zaterdag 14 maart 2009 @ 10:26:
Ik denk ook even mee, misschien kan de parsetijd nog omlaag.


[...]


Wat is hier uitgekomen?
Tevens gaat hij dit
PHP:
1
if($i == 0 OR $product_id[$i] != $product_id[$i-1]){

net zoveel keer doen als er rows uit de query komen. Ik denk dat daar nog snelheidswinst te behalen is.
Die vergelijking moet hij toch ook gewoon voor elke row maken? :?

'E's fighting in there!' he stuttered, grabbing the captain's arm.
'All by himself?' said the captain.
'No, with everyone!' shouted Nobby, hopping from one foot to the other.


Acties:
  • 0 Henk 'm!

  • Saven
  • Registratie: December 2006
  • Laatst online: 18:37

Saven

Administrator

Bart Brinkman schreef op vrijdag 13 maart 2009 @ 21:41:
[...]


Of het gebrek aan een goede index...
Met indexes kan het nog steeds sloom gaan.

Mijn forum-index (wordt tegewoordig wel serverside gecache't als plain html) doet er zo'n 6 seconden over om te genereren. Met meer dan 100.000 posts.

Of doe ik eigenlijk iets verkeerd en moet dit in 1 seconde ook kunnen :P

(lichtelijk offtopic vraag :$ :P)

[ Voor 4% gewijzigd door Saven op 14-03-2009 18:46 ]


Acties:
  • 0 Henk 'm!

  • CoolGamer
  • Registratie: Mei 2005
  • Laatst online: 18:08

CoolGamer

What is it? Dragons?

Saven schreef op zaterdag 14 maart 2009 @ 18:45:
[...]

Met indexes kan het nog steeds sloom gaan.

Mijn forum-index (wordt tegewoordig wel serverside gecache't als plain html) doet er zo'n 6 seconden over om te genereren. Met meer dan 100.000 posts.

Of doe ik eigenlijk iets verkeerd en moet dit in 1 seconde ook kunnen :P

(lichtelijk offtopic vraag :$ :P)
Zoek eens op "database index" i.p.v. forumindex. Dat zijn totaal verschillende dingen. Dus misschien kan er met een databaseindex wel wat tijd af van dat genereren.

Maar het zou natuurlijk ook gewoon kunnen dat je niet de juiste indexen hebt gekozen. Want 100.000 is niet zo heel veel.

[ Voor 9% gewijzigd door CoolGamer op 14-03-2009 18:52 ]

¸.·´¯`·.¸.·´¯`·.¸><(((º>¸.·´¯`·.¸><(((º>¸.·´¯`·.¸.·´¯`·.¸.·´¯`·.¸<º)))><¸.·´¯`·.¸.·´¯`·.¸.·´¯`·.¸


Acties:
  • 0 Henk 'm!

  • NMe
  • Registratie: Februari 2004
  • Laatst online: 09-09 13:58

NMe

Quia Ego Sic Dico.

Saven schreef op zaterdag 14 maart 2009 @ 18:45:
[...]

Of doe ik eigenlijk iets verkeerd en moet dit in 1 seconde ook kunnen :P

(lichtelijk offtopic vraag :$ :P)
Ten eerste is daar zonder datamodel inclusief gezette indices en zonder relevante queries niets over te zeggen, en ten tweede is dit je reinste topickaping en dus niet de bedoeling hier. Als je hier antwoord op wil hebben kun je je eigen topic openen. :)

'E's fighting in there!' he stuttered, grabbing the captain's arm.
'All by himself?' said the captain.
'No, with everyone!' shouted Nobby, hopping from one foot to the other.


Acties:
  • 0 Henk 'm!

  • Saven
  • Registratie: December 2006
  • Laatst online: 18:37

Saven

Administrator

TheCoolGamer schreef op zaterdag 14 maart 2009 @ 18:51:
[...]

Zoek eens op "database index" i.p.v. forumindex. Dat zijn totaal verschillende dingen. Dus misschien kan er met een databaseindex wel wat tijd af van dat genereren.

Maar het zou natuurlijk ook gewoon kunnen dat je niet de juiste indexen hebt gekozen. Want 100.000 is niet zo heel veel.
Haha no shit :P ik bedoelde forumindex-pagina en de bijbehorende database indexes.
Maari k maak straks wel een eigen topic :P excuzes moi voor de topic kaping O-)

Acties:
  • 0 Henk 'm!

  • LuCarD
  • Registratie: Januari 2000
  • Niet online

LuCarD

Certified BUFH

Je kan die mktime ook vervangen door 1 mktime. En dan voor alle vervolg dagen 86400 bij op tellen.

Programmer - an organism that turns coffee into software.


Acties:
  • 0 Henk 'm!

  • crisp
  • Registratie: Februari 2000
  • Nu online

crisp

Devver

Pixelated

LuCarD schreef op zaterdag 14 maart 2009 @ 23:49:
Je kan die mktime ook vervangen door 1 mktime. En dan voor alle vervolg dagen 86400 bij op tellen.
Nee; er is ook nog zoiets als zomer/wintertijd ;)

Het kan wel met 1 mktime() (en 1 date()) in de loop die nu het dagnummer en start/end timestamps per dag doet, maar dat is nu een functie met maar [dagen per maand] iteraties dus dat effect zal nog maar weinig merkbaar zijn:

PHP:
1
2
3
4
5
6
7
8
9
10
$year = date('Y');
$thisday = mktime (0,0,0,$maand,1,$year);
for($k = 1; $k < $dagen_in_maand; $k++)
{
    $weekdag[$k] = date('w', $thisday);
    $datum_a[$k] = $thisday;
    $datum_b[$k] = mktime (0,0,0,$maand,$k+1,$year);

    $thisday = $datum_b[$k];
}

[ Voor 49% gewijzigd door crisp op 14-03-2009 23:56 ]

Intentionally left blank


Acties:
  • 0 Henk 'm!

  • Bpje
  • Registratie: November 2000
  • Laatst online: 25-04 22:59
Volgens mij zou dit al wat winst op moeten leveren.

PHP:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
<?php

$year = date('Y');
$thisday = mktime (0,0,0,$maand,1,$year);

$dayOfTheMonth = date("d");
$month = date("m");

for($k = 1; $k < $dagen_in_maand; $k++)
{
    $weekdag[$k] = date('w', $thisday);
    $datum_a[$k] = $thisday;
    $datum_b[$k] = mktime (0,0,0,$maand,$k+1,$year);

    $thisday = $datum_b[$k];
} 


$html = '';

//Alle producten langslopen en een rij van weergeven
$p = 0; // variabele om om de 15 rijen de dagen vd week aan te geven
for($i = 0; $i < $num_rows; $i++){
    if($i == 0 OR $product_id[$i] != $product_id[$i-1]){
        
        // rij met dagen vd week neerzetten na iedere 15 regels
        if($p == 16){$p = 0; $html .= $maandrow;}
        $p++;
        
        $html .='
            <tr>
                <td width="30">'.$code[$i].'</td>
                <td width="150">'.$naam[$i].'</td>
        ';
        //Alle dagen van de week weergeven voor product[i]
        $j = $i;
        for($k = 1; $k < $dagen_in_maand; $k++){                        //loop alle dagen langs voor product i
            if(($datum_a[$k] <= $van[$j] AND $van[$j] <= $datum_b[$k])
            OR ($datum_a[$k] <= $tot[$j] AND $tot[$j] <= $datum_b[$k])
            OR ($van[$j] <= $datum_a[$k] AND $tot[$j] >= $datum_b[$k])){
                $html .= '<td class="beschikbaarheid_1">&nbsp;</td>'; //rood, oftewel niet beschikbaar
                if($tot[$j] < $datum_b[$k] AND $product_id[$j] == $product_id[$j+1]){$j++;}
            } else {
                if($k == $dayOfTheMonth and $maand == $month){    //huidige dag accentueren
                    $html .= '<td class="beschikbaarheid_vandaag">&nbsp;</td>';
                } elseif($weekdag[$k] == 6 or $weekdag[$k] == 0){        //weekend accentueren
                    $html .= '<td class="beschikbaarheid_0b">&nbsp;</td>';
                } else {
                    $html .= '<td class="beschikbaarheid_0">&nbsp;</td>'; //wit
                }
            }
        }
        $html .= '</tr>';
    }
} 
echo $html;

?>



Wat mij op viel was dat je " gebruikt ipv ' voor je echo's ' is iets sneller omdat bij " /n /t geparsed moet worden, Verder kun je proberen eerst alles in een variable op te vangen en vervolgens uit te poepen.

[ Voor 0% gewijzigd door Bpje op 18-03-2009 11:13 . Reden: was 1 echo vergeten ]


Acties:
  • 0 Henk 'm!

  • Voutloos
  • Registratie: Januari 2002
  • Niet online
Single vs double quotes is de meest beruchte micro optimalisatie en met in begrip van de tijd die je bezig bent om 58 regels te posten is er de komende 1,42 miljoen jaar nog geen netto winst... :P

Dat er eerder in het topic succes geboekt is is puur toeval/gokwerk geweest. Het enige echte antwoord op de vraag waar de meeste tijd in zit is en blijft profilen, profilen profilen.

{signature}


Acties:
  • 0 Henk 'm!

  • ACM
  • Registratie: Januari 2000
  • Niet online

ACM

Software Architect

Werkt hier

(jarig!)
Bpje schreef op woensdag 18 maart 2009 @ 09:18:
Volgens mij zou dit al wat winst op moeten leveren.
De winst van het reduceren van de date/time-calls (wat doorgaans vrij dure calls zijn) zal toch echt het grootste stuk winst opleveren.
Wat mij op viel was dat je " gebruikt ipv ' voor je echo's ' is iets sneller omdat bij " /n /t geparsed moet worden,
Dat is niet de belangrijkste reden dat " sneller kan zijn dan '. Sterker nog, vziw wordt het tot exact dezelfde interne phpcode geparsed als er geen $ tussen de "s voorkomt. Maar zelfs als wel alle variabelen inline staan is het nog maar een beperkte winst. Hoewel binnen je kritieke pad ook microoptimalisaties natuurlijk forse winsten kunnen opleveren.

Acties:
  • 0 Henk 'm!

Verwijderd

Waar vervolgens een geweldig antwoord op is gegeven. Tnx guys!

Ik programmeer zelf ook wel eens wat php en ik had een script draaien dat er 12 minuten over deed. Ik had zelfs al een mooi "bezig met laden" schermpje gemaakt voor de eindgebruiker inclusief schatting van de overgebleven tijd en % balkje dat volliep, omdat het echt schrikbarend lang duurde. Nooit in me opgekomen dat code ook efficiënter geschreven kon worden en dat de functies mktime en date in php zo langzaam waren.

Het betreffende script heeft extreem veel verwijzigen naar mktime en date, vandaar deze oplossing. een fuctie mktime_store erbij en find&replace mktime( naar mktime_store( et voila:
PHP:
1
2
3
4
5
6
7
8
9
function mktime_store($a,$b,$c,$d,$e,$f){
if(isset($_ENV['mktime'][$a][$b][$c][$d][$e][$f])){
return $_ENV['mktime'][$a][$b][$c][$d][$e][$f];
}
else{
$_ENV['mktime'][$a][$b][$c][$d][$e][$f] = mktime($a,$b,$c,$d,$e,$f);
return $_ENV['mktime'][$a][$b][$c][$d][$e][$f];
}
}

het bovenstaande heeft me teruggebracht van 12 naar 6 minuten.

Ik werd dolenthousiast en probeerde hetzelfde met het aanmaken van de functie date_store en deed een find&replace met date( naar date_store( et voila:
PHP:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
function date_store($a,&$b = '#'){
if(isset($_ENV['date'][$a][$b])){
return $_ENV['date'][$a][$b];
}
else{
if($b == '#'){
$_ENV['date'][$a][$b] = date($a);
}
else{
$_ENV['date'][$a][$b] = date($a,$b);
}
return $_ENV['date'][$a][$b];
}
}

Het tweede stukje code heeft me teruggebracht van 6 minuten naar 40 seconden.

In totaal dus nog maar 1/12 over: van 12 minuten naar 40 seconden _/-\o_

Wat ik me nu afvraag is of het misschien zelfs loont om ze allemaal in sql te zetten en in 1x eruit te halen en te gebruiken op dezelfde manier...

Acties:
  • 0 Henk 'm!

  • Voutloos
  • Registratie: Januari 2002
  • Niet online
En ook jij had gewoon moeten profilen. ;)

Extra tip, maar dat is niet per se vanwege de performance: Gebruik een static variabele ipv het misbruiken van $_ENV of $_GLOBALS. Misschien kan je ipv het binnen de functie cachen zelfs ook gewoon in de aanroepende code oplossen, door bijvoorbeeld een invariant niet binnen een loopje steeds opnieuw uit te rekenen.

offtopic:
En 40 seconden is 1/18e van 12 minuten. :+

{signature}


Acties:
  • 0 Henk 'm!

Verwijderd

Voutloos schreef op woensdag 18 maart 2009 @ 20:08:
En ook jij had gewoon moeten profilen. ;)

Extra tip, maar dat is niet per se vanwege de performance: Gebruik een static variabele ipv het misbruiken van $_ENV of $_GLOBALS. Misschien kan je ipv het binnen de functie cachen zelfs ook gewoon in de aanroepende code oplossen, door bijvoorbeeld een invariant niet binnen een loopje steeds opnieuw uit te rekenen.

offtopic:
En 40 seconden is 1/18e van 12 minuten. :+
Tnx voor de tip ;) het is voor nu wel even goed zo. Ik heb niet zo'n zin om al die calls aan te gaan passen (het zijn er echt heel veel) Dit was de makkelijkste manier voor nu.

offtopic:
ik had eerst 1 minuut opgeschreven, maar het bleek toch nog nèt iets sneller te zijn. Goeie toevoeging, dit is nog beter te verkopen :+

Acties:
  • 0 Henk 'm!

  • Woy
  • Registratie: April 2000
  • Niet online

Woy

Moderator Devschuur®
Verwijderd schreef op woensdag 18 maart 2009 @ 20:01:
[...]
Wat ik me nu afvraag is of het misschien zelfs loont om ze allemaal in sql te zetten en in 1x eruit te halen en te gebruiken op dezelfde manier...
Het zou inderdaad een oplossing kunnen zijn, om data redundant op te slaan. Je neemt dan bijvoorbeeld een extra veld in je tabel op, die de date al geformateerd opslaat. Laat overigens wel gewoon het Date field staan, want dat is de originele data.

Dit soort oplossingen moet je natuurlijk wel alleen doen, als je de bottleneck niet op een andere manier eenvoudig op kunt lossen.

Een nadeel daarvan is dat je wel minder flexibel word in je interface. Als je bijvoorbeeld straks ook in andere cultures wilt gaan formateren, is of je probleem weer terug, of je moet een hoop extra velden op gaan nemen.

Het is dus inderdaad van belang om eens te gaan profilen, of het restant van de 40 seconden executie tijd wel in mktime zit, en dat je niet ergens anders nog wat doet wat veel tijd kost.

“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!

  • Grijze Vos
  • Registratie: December 2002
  • Laatst online: 28-02 22:17
Of je slaat datums gewoon als datum op en houdt je pas bezig met de representatie van die datum in de presentatie-laag van je code. Ik kan me niet voorstellen dat je datamodel en je code enigszins zinnig zijn ingedeeld als je meervoudige loops hebt waar veelvuldig mktime en date worden aangeroepen.

Op zoek naar een nieuwe collega, .NET webdev, voornamelijk productontwikkeling. DM voor meer info


Acties:
  • 0 Henk 'm!

  • Voutloos
  • Registratie: Januari 2002
  • Niet online
Juist. Meer redundantie kan als last resort een leuke optimalisatie zijn, maar hier is het gewoon overduidelijk niet de Echte Oplossing.

{signature}


Acties:
  • 0 Henk 'm!

  • Woy
  • Registratie: April 2000
  • Niet online

Woy

Moderator Devschuur®
Voutloos schreef op donderdag 19 maart 2009 @ 13:21:
Juist. Meer redundantie kan als last resort een leuke optimalisatie zijn, maar hier is het gewoon overduidelijk niet de Echte Oplossing.
Het was idd niet mijn doel, om die oplossing hier als de juiste oplossing aan te dragen. Maar in sommige situaties kan het nou eenmaal nodig zijn om data redundant op te slaan.

“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.”

Pagina: 1